blob: f924c4a787603a7d02ae8339197fc621351471f4 [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 {
132 const OffsetBindingPointer<gl::Buffer> &buffer =
133 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
Geoff Langeb66a6e2016-10-31 13:06:12 -0400283 mGLState.initialize(mCaps, mExtensions, getClientVersion(), GetDebug(attribs),
Jamie Madille08a1d32017-03-07 17:24:06 -0500284 GetBindGeneratesResource(attribs), GetClientArraysEnabled(attribs),
Jamie Madill948bbe52017-06-01 13:10:42 -0400285 robustResourceInit);
Régis Fénéon83107972015-02-05 12:57:44 +0100286
Shannon Woods53a94a82014-06-24 15:20:36 -0400287 mFenceNVHandleAllocator.setBaseHandle(0);
Geoff Lang7dca1862013-07-30 16:30:46 -0400288
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000289 // [OpenGL ES 2.0.24] section 3.7 page 83:
290 // In the initial state, TEXTURE_2D and TEXTURE_CUBE_MAP have twodimensional
291 // and cube map texture state vectors respectively associated with them.
292 // In order that access to these initial textures not be lost, they are treated as texture
293 // objects all of whose names are 0.
294
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400295 Texture *zeroTexture2D = new Texture(mImplementation.get(), 0, GL_TEXTURE_2D);
Jamie Madilldedd7b92014-11-05 16:30:36 -0500296 mZeroTextures[GL_TEXTURE_2D].set(zeroTexture2D);
Jamie Madilldedd7b92014-11-05 16:30:36 -0500297
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400298 Texture *zeroTextureCube = new Texture(mImplementation.get(), 0, GL_TEXTURE_CUBE_MAP);
Jamie Madilldedd7b92014-11-05 16:30:36 -0500299 mZeroTextures[GL_TEXTURE_CUBE_MAP].set(zeroTextureCube);
Geoff Lang76b10c92014-09-05 16:28:14 -0400300
Geoff Langeb66a6e2016-10-31 13:06:12 -0400301 if (getClientVersion() >= Version(3, 0))
Geoff Lang76b10c92014-09-05 16:28:14 -0400302 {
303 // TODO: These could also be enabled via extension
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400304 Texture *zeroTexture3D = new Texture(mImplementation.get(), 0, GL_TEXTURE_3D);
Jamie Madilldedd7b92014-11-05 16:30:36 -0500305 mZeroTextures[GL_TEXTURE_3D].set(zeroTexture3D);
Geoff Lang76b10c92014-09-05 16:28:14 -0400306
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400307 Texture *zeroTexture2DArray = new Texture(mImplementation.get(), 0, GL_TEXTURE_2D_ARRAY);
Jamie Madilldedd7b92014-11-05 16:30:36 -0500308 mZeroTextures[GL_TEXTURE_2D_ARRAY].set(zeroTexture2DArray);
Geoff Lang76b10c92014-09-05 16:28:14 -0400309 }
Geoff Lang3b573612016-10-31 14:08:10 -0400310 if (getClientVersion() >= Version(3, 1))
311 {
312 Texture *zeroTexture2DMultisample =
313 new Texture(mImplementation.get(), 0, GL_TEXTURE_2D_MULTISAMPLE);
314 mZeroTextures[GL_TEXTURE_2D_MULTISAMPLE].set(zeroTexture2DMultisample);
Jiajia Qin6eafb042016-12-27 17:04:07 +0800315
316 bindGenericAtomicCounterBuffer(0);
317 for (unsigned int i = 0; i < mCaps.maxAtomicCounterBufferBindings; i++)
318 {
319 bindIndexedAtomicCounterBuffer(0, i, 0, 0);
320 }
Jiajia Qinf546e7d2017-03-27 14:12:59 +0800321
322 bindGenericShaderStorageBuffer(0);
323 for (unsigned int i = 0; i < mCaps.maxShaderStorageBufferBindings; i++)
324 {
325 bindIndexedShaderStorageBuffer(0, i, 0, 0);
326 }
Geoff Lang3b573612016-10-31 14:08:10 -0400327 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000328
Ian Ewellbda75592016-04-18 17:25:54 -0400329 if (mExtensions.eglImageExternal || mExtensions.eglStreamConsumerExternal)
330 {
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400331 Texture *zeroTextureExternal =
332 new Texture(mImplementation.get(), 0, GL_TEXTURE_EXTERNAL_OES);
Ian Ewellbda75592016-04-18 17:25:54 -0400333 mZeroTextures[GL_TEXTURE_EXTERNAL_OES].set(zeroTextureExternal);
334 }
335
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700336 mGLState.initializeZeroTextures(mZeroTextures);
Jamie Madille6382c32014-11-07 15:05:26 -0500337
Jamie Madill57a89722013-07-02 11:57:03 -0400338 bindVertexArray(0);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000339 bindArrayBuffer(0);
Jiajia Qin9d7d0b12016-11-29 16:30:31 +0800340 bindDrawIndirectBuffer(0);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000341 bindElementArrayBuffer(0);
Geoff Lang76b10c92014-09-05 16:28:14 -0400342
Jamie Madill01a80ee2016-11-07 12:06:18 -0500343 bindRenderbuffer(GL_RENDERBUFFER, 0);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000344
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +0000345 bindGenericUniformBuffer(0);
Geoff Lang4dc3af02016-11-18 14:09:27 -0500346 for (unsigned int i = 0; i < mCaps.maxUniformBufferBindings; i++)
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +0000347 {
348 bindIndexedUniformBuffer(0, i, 0, -1);
349 }
350
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +0000351 bindCopyReadBuffer(0);
352 bindCopyWriteBuffer(0);
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +0000353 bindPixelPackBuffer(0);
354 bindPixelUnpackBuffer(0);
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +0000355
Geoff Langeb66a6e2016-10-31 13:06:12 -0400356 if (getClientVersion() >= Version(3, 0))
Geoff Lang1a683462015-09-29 15:09:59 -0400357 {
358 // [OpenGL ES 3.0.2] section 2.14.1 pg 85:
359 // In the initial state, a default transform feedback object is bound and treated as
360 // a transform feedback object with a name of zero. That object is bound any time
361 // BindTransformFeedback is called with id of zero
Geoff Lang1a683462015-09-29 15:09:59 -0400362 bindTransformFeedback(0);
363 }
Geoff Langc8058452014-02-03 12:04:11 -0500364
Jamie Madillad9f24e2016-02-12 09:27:24 -0500365 // Initialize dirty bit masks
366 // TODO(jmadill): additional ES3 state
367 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_ALIGNMENT);
368 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_ROW_LENGTH);
369 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_IMAGE_HEIGHT);
370 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_SKIP_IMAGES);
371 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_SKIP_ROWS);
372 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_SKIP_PIXELS);
Corentin Wallezbbd663a2016-04-20 17:49:17 -0400373 mTexImageDirtyBits.set(State::DIRTY_BIT_UNPACK_BUFFER_BINDING);
Jamie Madillad9f24e2016-02-12 09:27:24 -0500374 // No dirty objects.
375
376 // Readpixels uses the pack state and read FBO
377 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_ALIGNMENT);
378 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_REVERSE_ROW_ORDER);
379 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_ROW_LENGTH);
380 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_SKIP_ROWS);
381 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_SKIP_PIXELS);
Corentin Wallezbbd663a2016-04-20 17:49:17 -0400382 mReadPixelsDirtyBits.set(State::DIRTY_BIT_PACK_BUFFER_BINDING);
Jamie Madillad9f24e2016-02-12 09:27:24 -0500383 mReadPixelsDirtyObjects.set(State::DIRTY_OBJECT_READ_FRAMEBUFFER);
384
385 mClearDirtyBits.set(State::DIRTY_BIT_RASTERIZER_DISCARD_ENABLED);
386 mClearDirtyBits.set(State::DIRTY_BIT_SCISSOR_TEST_ENABLED);
387 mClearDirtyBits.set(State::DIRTY_BIT_SCISSOR);
388 mClearDirtyBits.set(State::DIRTY_BIT_VIEWPORT);
389 mClearDirtyBits.set(State::DIRTY_BIT_CLEAR_COLOR);
390 mClearDirtyBits.set(State::DIRTY_BIT_CLEAR_DEPTH);
391 mClearDirtyBits.set(State::DIRTY_BIT_CLEAR_STENCIL);
392 mClearDirtyBits.set(State::DIRTY_BIT_COLOR_MASK);
393 mClearDirtyBits.set(State::DIRTY_BIT_DEPTH_MASK);
394 mClearDirtyBits.set(State::DIRTY_BIT_STENCIL_WRITEMASK_FRONT);
395 mClearDirtyBits.set(State::DIRTY_BIT_STENCIL_WRITEMASK_BACK);
396 mClearDirtyObjects.set(State::DIRTY_OBJECT_DRAW_FRAMEBUFFER);
397
398 mBlitDirtyBits.set(State::DIRTY_BIT_SCISSOR_TEST_ENABLED);
399 mBlitDirtyBits.set(State::DIRTY_BIT_SCISSOR);
Geoff Lang1d2c41d2016-10-19 16:14:46 -0700400 mBlitDirtyBits.set(State::DIRTY_BIT_FRAMEBUFFER_SRGB);
Jamie Madillad9f24e2016-02-12 09:27:24 -0500401 mBlitDirtyObjects.set(State::DIRTY_OBJECT_READ_FRAMEBUFFER);
402 mBlitDirtyObjects.set(State::DIRTY_OBJECT_DRAW_FRAMEBUFFER);
Jamie Madill437fa652016-05-03 15:13:24 -0400403
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400404 handleError(mImplementation->initialize());
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000405}
406
Jamie Madill70ee0f62017-02-06 16:04:20 -0500407void Context::destroy(egl::Display *display)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000408{
Jamie Madill6c1f6712017-02-14 19:08:04 -0500409 mGLState.reset(this);
Geoff Lang21329412014-12-02 20:50:30 +0000410
Corentin Wallez80b24112015-08-25 16:41:57 -0400411 for (auto fence : mFenceNVMap)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000412 {
Corentin Wallez80b24112015-08-25 16:41:57 -0400413 SafeDelete(fence.second);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000414 }
415
Corentin Wallez80b24112015-08-25 16:41:57 -0400416 for (auto query : mQueryMap)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000417 {
Geoff Langf0aa8422015-09-29 15:08:34 -0400418 if (query.second != nullptr)
419 {
420 query.second->release();
421 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000422 }
423
Corentin Wallez80b24112015-08-25 16:41:57 -0400424 for (auto vertexArray : mVertexArrayMap)
Jamie Madill57a89722013-07-02 11:57:03 -0400425 {
Corentin Wallez80b24112015-08-25 16:41:57 -0400426 SafeDelete(vertexArray.second);
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 {
Yunchao Hef81ce4a2017-04-24 10:49:17 +0800439 zeroTexture.second.set(nullptr);
Geoff Lang76b10c92014-09-05 16:28:14 -0400440 }
441 mZeroTextures.clear();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000442
Corentin Wallezccab69d2017-01-27 16:57:15 -0500443 SafeDelete(mSurfacelessFramebuffer);
444
Jamie Madill70ee0f62017-02-06 16:04:20 -0500445 releaseSurface(display);
Jamie Madill2f348d22017-06-05 10:50:59 -0400446 releaseShaderCompiler();
Jamie Madill6c1f6712017-02-14 19:08:04 -0500447
448 mState.mBuffers->release(this);
449 mState.mShaderPrograms->release(this);
450 mState.mTextures->release(this);
451 mState.mRenderbuffers->release(this);
452 mState.mSamplers->release(this);
453 mState.mFenceSyncs->release(this);
454 mState.mPaths->release(this);
455 mState.mFramebuffers->release(this);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000456}
457
Jamie Madill70ee0f62017-02-06 16:04:20 -0500458Context::~Context()
459{
460}
461
462void Context::makeCurrent(egl::Display *display, egl::Surface *surface)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000463{
Jamie Madill61e16b42017-06-19 11:13:23 -0400464 mCurrentDisplay = display;
465
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000466 if (!mHasBeenCurrent)
467 {
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000468 initRendererString();
Geoff Langc339c4e2016-11-29 10:37:36 -0500469 initVersionStrings();
Geoff Langcec35902014-04-16 10:52:36 -0400470 initExtensionStrings();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000471
Corentin Wallezc295e512017-01-27 17:47:50 -0500472 int width = 0;
473 int height = 0;
474 if (surface != nullptr)
475 {
476 width = surface->getWidth();
477 height = surface->getHeight();
478 }
479
480 mGLState.setViewportParams(0, 0, width, height);
481 mGLState.setScissorParams(0, 0, width, height);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000482
483 mHasBeenCurrent = true;
484 }
485
Jamie Madill1b94d432015-08-07 13:23:23 -0400486 // TODO(jmadill): Rework this when we support ContextImpl
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700487 mGLState.setAllDirtyBits();
Jamie Madill1b94d432015-08-07 13:23:23 -0400488
Jamie Madill70ee0f62017-02-06 16:04:20 -0500489 releaseSurface(display);
Corentin Wallezccab69d2017-01-27 16:57:15 -0500490
491 Framebuffer *newDefault = nullptr;
492 if (surface != nullptr)
493 {
Jamie Madill70ee0f62017-02-06 16:04:20 -0500494 surface->setIsCurrent(display, true);
Corentin Wallezccab69d2017-01-27 16:57:15 -0500495 mCurrentSurface = surface;
496 newDefault = surface->getDefaultFramebuffer();
497 }
498 else
499 {
500 if (mSurfacelessFramebuffer == nullptr)
501 {
502 mSurfacelessFramebuffer = new Framebuffer(mImplementation.get());
503 }
504
505 newDefault = mSurfacelessFramebuffer;
506 }
Jamie Madill18fdcbc2015-08-19 18:12:44 +0000507
Corentin Wallez37c39792015-08-20 14:19:46 -0400508 // Update default framebuffer, the binding of the previous default
509 // framebuffer (or lack of) will have a nullptr.
Jamie Madillc1c1cdc2015-04-30 09:42:26 -0400510 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700511 if (mGLState.getReadFramebuffer() == nullptr)
Corentin Wallez37c39792015-08-20 14:19:46 -0400512 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700513 mGLState.setReadFramebufferBinding(newDefault);
Corentin Wallez37c39792015-08-20 14:19:46 -0400514 }
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700515 if (mGLState.getDrawFramebuffer() == nullptr)
Corentin Wallez37c39792015-08-20 14:19:46 -0400516 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700517 mGLState.setDrawFramebufferBinding(newDefault);
Corentin Wallez37c39792015-08-20 14:19:46 -0400518 }
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500519 mState.mFramebuffers->setDefaultFramebuffer(newDefault);
Jamie Madillc1c1cdc2015-04-30 09:42:26 -0400520 }
Ian Ewell292f0052016-02-04 10:37:32 -0500521
522 // Notify the renderer of a context switch
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700523 mImplementation->onMakeCurrent(mState);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000524}
525
Jamie Madill70ee0f62017-02-06 16:04:20 -0500526void Context::releaseSurface(egl::Display *display)
Jamie Madill77a72f62015-04-14 11:18:32 -0400527{
Corentin Wallez37c39792015-08-20 14:19:46 -0400528 // Remove the default framebuffer
Corentin Wallezc295e512017-01-27 17:47:50 -0500529 Framebuffer *currentDefault = nullptr;
530 if (mCurrentSurface != nullptr)
Corentin Wallez51706ea2015-08-07 14:39:22 -0400531 {
Corentin Wallezc295e512017-01-27 17:47:50 -0500532 currentDefault = mCurrentSurface->getDefaultFramebuffer();
533 }
534 else if (mSurfacelessFramebuffer != nullptr)
535 {
536 currentDefault = mSurfacelessFramebuffer;
Corentin Wallez51706ea2015-08-07 14:39:22 -0400537 }
538
Corentin Wallezc295e512017-01-27 17:47:50 -0500539 if (mGLState.getReadFramebuffer() == currentDefault)
540 {
541 mGLState.setReadFramebufferBinding(nullptr);
542 }
543 if (mGLState.getDrawFramebuffer() == currentDefault)
544 {
545 mGLState.setDrawFramebufferBinding(nullptr);
546 }
547 mState.mFramebuffers->setDefaultFramebuffer(nullptr);
548
549 if (mCurrentSurface)
550 {
Jamie Madill70ee0f62017-02-06 16:04:20 -0500551 mCurrentSurface->setIsCurrent(display, false);
Corentin Wallezc295e512017-01-27 17:47:50 -0500552 mCurrentSurface = nullptr;
553 }
Jamie Madill77a72f62015-04-14 11:18:32 -0400554}
555
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000556GLuint Context::createBuffer()
557{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500558 return mState.mBuffers->createBuffer();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000559}
560
561GLuint Context::createProgram()
562{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500563 return mState.mShaderPrograms->createProgram(mImplementation.get());
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000564}
565
566GLuint Context::createShader(GLenum type)
567{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500568 return mState.mShaderPrograms->createShader(mImplementation.get(), mLimitations, type);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000569}
570
571GLuint Context::createTexture()
572{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500573 return mState.mTextures->createTexture();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000574}
575
576GLuint Context::createRenderbuffer()
577{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500578 return mState.mRenderbuffers->createRenderbuffer();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000579}
580
Geoff Lang882033e2014-09-30 11:26:07 -0400581GLsync Context::createFenceSync()
Jamie Madillcd055f82013-07-26 11:55:15 -0400582{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500583 GLuint handle = mState.mFenceSyncs->createFenceSync(mImplementation.get());
Jamie Madillcd055f82013-07-26 11:55:15 -0400584
Cooper Partind8e62a32015-01-29 15:21:25 -0800585 return reinterpret_cast<GLsync>(static_cast<uintptr_t>(handle));
Jamie Madillcd055f82013-07-26 11:55:15 -0400586}
587
Sami Väisänene45e53b2016-05-25 10:36:04 +0300588GLuint Context::createPaths(GLsizei range)
589{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500590 auto resultOrError = mState.mPaths->createPaths(mImplementation.get(), range);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300591 if (resultOrError.isError())
592 {
593 handleError(resultOrError.getError());
594 return 0;
595 }
596 return resultOrError.getResult();
597}
598
Jamie Madill57a89722013-07-02 11:57:03 -0400599GLuint Context::createVertexArray()
600{
Geoff Lang36167ab2015-12-07 10:27:14 -0500601 GLuint vertexArray = mVertexArrayHandleAllocator.allocate();
602 mVertexArrayMap[vertexArray] = nullptr;
603 return vertexArray;
Jamie Madill57a89722013-07-02 11:57:03 -0400604}
605
Jamie Madilldc356042013-07-19 16:36:57 -0400606GLuint Context::createSampler()
607{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500608 return mState.mSamplers->createSampler();
Jamie Madilldc356042013-07-19 16:36:57 -0400609}
610
Geoff Langc8058452014-02-03 12:04:11 -0500611GLuint Context::createTransformFeedback()
612{
Geoff Lang36167ab2015-12-07 10:27:14 -0500613 GLuint transformFeedback = mTransformFeedbackAllocator.allocate();
614 mTransformFeedbackMap[transformFeedback] = nullptr;
615 return transformFeedback;
Geoff Langc8058452014-02-03 12:04:11 -0500616}
617
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000618// Returns an unused framebuffer name
619GLuint Context::createFramebuffer()
620{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500621 return mState.mFramebuffers->createFramebuffer();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000622}
623
Jamie Madill33dc8432013-07-26 11:55:05 -0400624GLuint Context::createFenceNV()
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000625{
Jamie Madill33dc8432013-07-26 11:55:05 -0400626 GLuint handle = mFenceNVHandleAllocator.allocate();
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000627
Jamie Madill53ea9cc2016-05-17 10:12:52 -0400628 mFenceNVMap[handle] = new FenceNV(mImplementation->createFenceNV());
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000629
630 return handle;
631}
632
633// Returns an unused query name
634GLuint Context::createQuery()
635{
636 GLuint handle = mQueryHandleAllocator.allocate();
637
Yunchao Hed7297bf2017-04-19 15:27:10 +0800638 mQueryMap[handle] = nullptr;
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000639
640 return handle;
641}
642
643void Context::deleteBuffer(GLuint buffer)
644{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500645 if (mState.mBuffers->getBuffer(buffer))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000646 {
647 detachBuffer(buffer);
648 }
Jamie Madill893ab082014-05-16 16:56:10 -0400649
Jamie Madill6c1f6712017-02-14 19:08:04 -0500650 mState.mBuffers->deleteObject(this, buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000651}
652
653void Context::deleteShader(GLuint shader)
654{
Jamie Madill6c1f6712017-02-14 19:08:04 -0500655 mState.mShaderPrograms->deleteShader(this, shader);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000656}
657
658void Context::deleteProgram(GLuint program)
659{
Jamie Madill6c1f6712017-02-14 19:08:04 -0500660 mState.mShaderPrograms->deleteProgram(this, program);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000661}
662
663void Context::deleteTexture(GLuint texture)
664{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500665 if (mState.mTextures->getTexture(texture))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000666 {
667 detachTexture(texture);
668 }
669
Jamie Madill6c1f6712017-02-14 19:08:04 -0500670 mState.mTextures->deleteObject(this, texture);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000671}
672
673void Context::deleteRenderbuffer(GLuint renderbuffer)
674{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500675 if (mState.mRenderbuffers->getRenderbuffer(renderbuffer))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000676 {
677 detachRenderbuffer(renderbuffer);
678 }
Jamie Madill893ab082014-05-16 16:56:10 -0400679
Jamie Madill6c1f6712017-02-14 19:08:04 -0500680 mState.mRenderbuffers->deleteObject(this, renderbuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000681}
682
Jamie Madillcd055f82013-07-26 11:55:15 -0400683void Context::deleteFenceSync(GLsync fenceSync)
684{
685 // The spec specifies the underlying Fence object is not deleted until all current
686 // wait commands finish. However, since the name becomes invalid, we cannot query the fence,
687 // and since our API is currently designed for being called from a single thread, we can delete
688 // the fence immediately.
Jamie Madill6c1f6712017-02-14 19:08:04 -0500689 mState.mFenceSyncs->deleteObject(this,
690 static_cast<GLuint>(reinterpret_cast<uintptr_t>(fenceSync)));
Jamie Madillcd055f82013-07-26 11:55:15 -0400691}
692
Sami Väisänene45e53b2016-05-25 10:36:04 +0300693void Context::deletePaths(GLuint first, GLsizei range)
694{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500695 mState.mPaths->deletePaths(first, range);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300696}
697
698bool Context::hasPathData(GLuint path) const
699{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500700 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300701 if (pathObj == nullptr)
702 return false;
703
704 return pathObj->hasPathData();
705}
706
707bool Context::hasPath(GLuint path) const
708{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500709 return mState.mPaths->hasPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300710}
711
712void Context::setPathCommands(GLuint path,
713 GLsizei numCommands,
714 const GLubyte *commands,
715 GLsizei numCoords,
716 GLenum coordType,
717 const void *coords)
718{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500719 auto *pathObject = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300720
721 handleError(pathObject->setCommands(numCommands, commands, numCoords, coordType, coords));
722}
723
724void Context::setPathParameterf(GLuint path, GLenum pname, GLfloat value)
725{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500726 auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300727
728 switch (pname)
729 {
730 case GL_PATH_STROKE_WIDTH_CHROMIUM:
731 pathObj->setStrokeWidth(value);
732 break;
733 case GL_PATH_END_CAPS_CHROMIUM:
734 pathObj->setEndCaps(static_cast<GLenum>(value));
735 break;
736 case GL_PATH_JOIN_STYLE_CHROMIUM:
737 pathObj->setJoinStyle(static_cast<GLenum>(value));
738 break;
739 case GL_PATH_MITER_LIMIT_CHROMIUM:
740 pathObj->setMiterLimit(value);
741 break;
742 case GL_PATH_STROKE_BOUND_CHROMIUM:
743 pathObj->setStrokeBound(value);
744 break;
745 default:
746 UNREACHABLE();
747 break;
748 }
749}
750
751void Context::getPathParameterfv(GLuint path, GLenum pname, GLfloat *value) const
752{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500753 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +0300754
755 switch (pname)
756 {
757 case GL_PATH_STROKE_WIDTH_CHROMIUM:
758 *value = pathObj->getStrokeWidth();
759 break;
760 case GL_PATH_END_CAPS_CHROMIUM:
761 *value = static_cast<GLfloat>(pathObj->getEndCaps());
762 break;
763 case GL_PATH_JOIN_STYLE_CHROMIUM:
764 *value = static_cast<GLfloat>(pathObj->getJoinStyle());
765 break;
766 case GL_PATH_MITER_LIMIT_CHROMIUM:
767 *value = pathObj->getMiterLimit();
768 break;
769 case GL_PATH_STROKE_BOUND_CHROMIUM:
770 *value = pathObj->getStrokeBound();
771 break;
772 default:
773 UNREACHABLE();
774 break;
775 }
776}
777
778void Context::setPathStencilFunc(GLenum func, GLint ref, GLuint mask)
779{
780 mGLState.setPathStencilFunc(func, ref, mask);
781}
782
Jamie Madill57a89722013-07-02 11:57:03 -0400783void Context::deleteVertexArray(GLuint vertexArray)
784{
Geoff Lang36167ab2015-12-07 10:27:14 -0500785 auto iter = mVertexArrayMap.find(vertexArray);
786 if (iter != mVertexArrayMap.end())
Geoff Lang50b3fe82015-12-08 14:49:12 +0000787 {
Geoff Lang36167ab2015-12-07 10:27:14 -0500788 VertexArray *vertexArrayObject = iter->second;
789 if (vertexArrayObject != nullptr)
790 {
791 detachVertexArray(vertexArray);
792 delete vertexArrayObject;
793 }
Geoff Lang50b3fe82015-12-08 14:49:12 +0000794
Geoff Lang36167ab2015-12-07 10:27:14 -0500795 mVertexArrayMap.erase(iter);
796 mVertexArrayHandleAllocator.release(vertexArray);
Jamie Madill57a89722013-07-02 11:57:03 -0400797 }
798}
799
Jamie Madilldc356042013-07-19 16:36:57 -0400800void Context::deleteSampler(GLuint sampler)
801{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500802 if (mState.mSamplers->getSampler(sampler))
Jamie Madilldc356042013-07-19 16:36:57 -0400803 {
804 detachSampler(sampler);
805 }
806
Jamie Madill6c1f6712017-02-14 19:08:04 -0500807 mState.mSamplers->deleteObject(this, sampler);
Jamie Madilldc356042013-07-19 16:36:57 -0400808}
809
Geoff Langc8058452014-02-03 12:04:11 -0500810void Context::deleteTransformFeedback(GLuint transformFeedback)
811{
Geoff Lang6e60d6b2017-04-12 12:59:04 -0400812 if (transformFeedback == 0)
813 {
814 return;
815 }
816
Jamie Madill5fd0b2d2015-01-05 13:38:44 -0500817 auto iter = mTransformFeedbackMap.find(transformFeedback);
Geoff Langc8058452014-02-03 12:04:11 -0500818 if (iter != mTransformFeedbackMap.end())
819 {
Geoff Lang36167ab2015-12-07 10:27:14 -0500820 TransformFeedback *transformFeedbackObject = iter->second;
821 if (transformFeedbackObject != nullptr)
822 {
823 detachTransformFeedback(transformFeedback);
Jamie Madill6c1f6712017-02-14 19:08:04 -0500824 transformFeedbackObject->release(this);
Geoff Lang36167ab2015-12-07 10:27:14 -0500825 }
826
Geoff Lang50b3fe82015-12-08 14:49:12 +0000827 mTransformFeedbackMap.erase(iter);
Geoff Lang36167ab2015-12-07 10:27:14 -0500828 mTransformFeedbackAllocator.release(transformFeedback);
Geoff Langc8058452014-02-03 12:04:11 -0500829 }
830}
831
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000832void Context::deleteFramebuffer(GLuint framebuffer)
833{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500834 if (mState.mFramebuffers->getFramebuffer(framebuffer))
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000835 {
836 detachFramebuffer(framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000837 }
Geoff Lang3bf8e3a2016-12-01 17:28:52 -0500838
Jamie Madill6c1f6712017-02-14 19:08:04 -0500839 mState.mFramebuffers->deleteObject(this, framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000840}
841
Jamie Madill33dc8432013-07-26 11:55:05 -0400842void Context::deleteFenceNV(GLuint fence)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000843{
Jamie Madill4e25a0d2016-03-08 13:53:03 -0500844 auto fenceObject = mFenceNVMap.find(fence);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000845
Jamie Madill33dc8432013-07-26 11:55:05 -0400846 if (fenceObject != mFenceNVMap.end())
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000847 {
Jamie Madill33dc8432013-07-26 11:55:05 -0400848 mFenceNVHandleAllocator.release(fenceObject->first);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000849 delete fenceObject->second;
Jamie Madill33dc8432013-07-26 11:55:05 -0400850 mFenceNVMap.erase(fenceObject);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000851 }
852}
853
854void Context::deleteQuery(GLuint query)
855{
Jamie Madill4e25a0d2016-03-08 13:53:03 -0500856 auto queryObject = mQueryMap.find(query);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000857 if (queryObject != mQueryMap.end())
858 {
859 mQueryHandleAllocator.release(queryObject->first);
860 if (queryObject->second)
861 {
862 queryObject->second->release();
863 }
864 mQueryMap.erase(queryObject);
865 }
866}
867
Geoff Lang70d0f492015-12-10 17:45:46 -0500868Buffer *Context::getBuffer(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000869{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500870 return mState.mBuffers->getBuffer(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000871}
872
Jamie Madill570f7c82014-07-03 10:38:54 -0400873Texture *Context::getTexture(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000874{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500875 return mState.mTextures->getTexture(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000876}
877
Geoff Lang70d0f492015-12-10 17:45:46 -0500878Renderbuffer *Context::getRenderbuffer(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000879{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500880 return mState.mRenderbuffers->getRenderbuffer(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000881}
882
Jamie Madillcd055f82013-07-26 11:55:15 -0400883FenceSync *Context::getFenceSync(GLsync handle) const
884{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500885 return mState.mFenceSyncs->getFenceSync(
886 static_cast<GLuint>(reinterpret_cast<uintptr_t>(handle)));
Jamie Madillcd055f82013-07-26 11:55:15 -0400887}
888
Jamie Madill57a89722013-07-02 11:57:03 -0400889VertexArray *Context::getVertexArray(GLuint handle) const
890{
891 auto vertexArray = mVertexArrayMap.find(handle);
Geoff Lang36167ab2015-12-07 10:27:14 -0500892 return (vertexArray != mVertexArrayMap.end()) ? vertexArray->second : nullptr;
Jamie Madill57a89722013-07-02 11:57:03 -0400893}
894
Jamie Madilldc356042013-07-19 16:36:57 -0400895Sampler *Context::getSampler(GLuint handle) const
896{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500897 return mState.mSamplers->getSampler(handle);
Jamie Madilldc356042013-07-19 16:36:57 -0400898}
899
Geoff Langc8058452014-02-03 12:04:11 -0500900TransformFeedback *Context::getTransformFeedback(GLuint handle) const
901{
Geoff Lang36167ab2015-12-07 10:27:14 -0500902 auto iter = mTransformFeedbackMap.find(handle);
903 return (iter != mTransformFeedbackMap.end()) ? iter->second : nullptr;
Geoff Langc8058452014-02-03 12:04:11 -0500904}
905
Geoff Lang70d0f492015-12-10 17:45:46 -0500906LabeledObject *Context::getLabeledObject(GLenum identifier, GLuint name) const
907{
908 switch (identifier)
909 {
910 case GL_BUFFER:
911 return getBuffer(name);
912 case GL_SHADER:
913 return getShader(name);
914 case GL_PROGRAM:
915 return getProgram(name);
916 case GL_VERTEX_ARRAY:
917 return getVertexArray(name);
918 case GL_QUERY:
919 return getQuery(name);
920 case GL_TRANSFORM_FEEDBACK:
921 return getTransformFeedback(name);
922 case GL_SAMPLER:
923 return getSampler(name);
924 case GL_TEXTURE:
925 return getTexture(name);
926 case GL_RENDERBUFFER:
927 return getRenderbuffer(name);
928 case GL_FRAMEBUFFER:
929 return getFramebuffer(name);
930 default:
931 UNREACHABLE();
932 return nullptr;
933 }
934}
935
936LabeledObject *Context::getLabeledObjectFromPtr(const void *ptr) const
937{
938 return getFenceSync(reinterpret_cast<GLsync>(const_cast<void *>(ptr)));
939}
940
Martin Radev9d901792016-07-15 15:58:58 +0300941void Context::objectLabel(GLenum identifier, GLuint name, GLsizei length, const GLchar *label)
942{
943 LabeledObject *object = getLabeledObject(identifier, name);
944 ASSERT(object != nullptr);
945
946 std::string labelName = GetObjectLabelFromPointer(length, label);
947 object->setLabel(labelName);
948}
949
950void Context::objectPtrLabel(const void *ptr, GLsizei length, const GLchar *label)
951{
952 LabeledObject *object = getLabeledObjectFromPtr(ptr);
953 ASSERT(object != nullptr);
954
955 std::string labelName = GetObjectLabelFromPointer(length, label);
956 object->setLabel(labelName);
957}
958
959void Context::getObjectLabel(GLenum identifier,
960 GLuint name,
961 GLsizei bufSize,
962 GLsizei *length,
963 GLchar *label) const
964{
965 LabeledObject *object = getLabeledObject(identifier, name);
966 ASSERT(object != nullptr);
967
968 const std::string &objectLabel = object->getLabel();
969 GetObjectLabelBase(objectLabel, bufSize, length, label);
970}
971
972void Context::getObjectPtrLabel(const void *ptr,
973 GLsizei bufSize,
974 GLsizei *length,
975 GLchar *label) const
976{
977 LabeledObject *object = getLabeledObjectFromPtr(ptr);
978 ASSERT(object != nullptr);
979
980 const std::string &objectLabel = object->getLabel();
981 GetObjectLabelBase(objectLabel, bufSize, length, label);
982}
983
Jamie Madilldc356042013-07-19 16:36:57 -0400984bool Context::isSampler(GLuint samplerName) const
985{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500986 return mState.mSamplers->isSampler(samplerName);
Jamie Madilldc356042013-07-19 16:36:57 -0400987}
988
Jamie Madill3f01e6c2016-03-08 13:53:02 -0500989void Context::bindArrayBuffer(GLuint bufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000990{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500991 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -0700992 mGLState.setArrayBufferBinding(buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +0000993}
994
Jiajia Qin9d7d0b12016-11-29 16:30:31 +0800995void Context::bindDrawIndirectBuffer(GLuint bufferHandle)
996{
Geoff Lang4ddf5af2016-12-01 14:30:44 -0500997 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jiajia Qin9d7d0b12016-11-29 16:30:31 +0800998 mGLState.setDrawIndirectBufferBinding(buffer);
999}
1000
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001001void Context::bindElementArrayBuffer(GLuint bufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001002{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001003 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Shao80957d92017-02-20 21:25:59 +08001004 mGLState.setElementArrayBuffer(buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001005}
1006
Jamie Madilldedd7b92014-11-05 16:30:36 -05001007void Context::bindTexture(GLenum target, GLuint handle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001008{
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001009 Texture *texture = nullptr;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001010
Jamie Madilldedd7b92014-11-05 16:30:36 -05001011 if (handle == 0)
1012 {
1013 texture = mZeroTextures[target].get();
1014 }
1015 else
1016 {
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001017 texture = mState.mTextures->checkTextureAllocation(mImplementation.get(), handle, target);
Jamie Madilldedd7b92014-11-05 16:30:36 -05001018 }
1019
1020 ASSERT(texture);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001021 mGLState.setSamplerTexture(target, texture);
shannon.woods%transgaming.com@gtempaccount.com90dbc442013-04-13 03:46:14 +00001022}
1023
Jamie Madill5bf9ff42016-02-01 11:13:03 -05001024void Context::bindReadFramebuffer(GLuint framebufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001025{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05001026 Framebuffer *framebuffer = mState.mFramebuffers->checkFramebufferAllocation(
1027 mImplementation.get(), mCaps, framebufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001028 mGLState.setReadFramebufferBinding(framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001029}
1030
Jamie Madill5bf9ff42016-02-01 11:13:03 -05001031void Context::bindDrawFramebuffer(GLuint framebufferHandle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001032{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05001033 Framebuffer *framebuffer = mState.mFramebuffers->checkFramebufferAllocation(
1034 mImplementation.get(), mCaps, framebufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001035 mGLState.setDrawFramebufferBinding(framebuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001036}
1037
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001038void Context::bindVertexArray(GLuint vertexArrayHandle)
Jamie Madill57a89722013-07-02 11:57:03 -04001039{
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001040 VertexArray *vertexArray = checkVertexArrayAllocation(vertexArrayHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001041 mGLState.setVertexArrayBinding(vertexArray);
Jamie Madill57a89722013-07-02 11:57:03 -04001042}
1043
Shao80957d92017-02-20 21:25:59 +08001044void Context::bindVertexBuffer(GLuint bindingIndex,
1045 GLuint bufferHandle,
1046 GLintptr offset,
1047 GLsizei stride)
1048{
1049 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
1050 mGLState.bindVertexBuffer(bindingIndex, buffer, offset, stride);
1051}
1052
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001053void Context::bindSampler(GLuint textureUnit, GLuint samplerHandle)
Jamie Madilldc356042013-07-19 16:36:57 -04001054{
Geoff Lang76b10c92014-09-05 16:28:14 -04001055 ASSERT(textureUnit < mCaps.maxCombinedTextureImageUnits);
Jamie Madill901b3792016-05-26 09:20:40 -04001056 Sampler *sampler =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001057 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), samplerHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001058 mGLState.setSamplerBinding(textureUnit, sampler);
Jamie Madilldc356042013-07-19 16:36:57 -04001059}
1060
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001061void Context::bindGenericUniformBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001062{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001063 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001064 mGLState.setGenericUniformBufferBinding(buffer);
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001065}
1066
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001067void Context::bindIndexedUniformBuffer(GLuint bufferHandle,
1068 GLuint index,
1069 GLintptr offset,
1070 GLsizeiptr size)
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001071{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001072 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001073 mGLState.setIndexedUniformBufferBinding(index, buffer, offset, size);
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001074}
1075
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001076void Context::bindGenericTransformFeedbackBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001077{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001078 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001079 mGLState.getCurrentTransformFeedback()->bindGenericBuffer(buffer);
shannon.woods%transgaming.com@gtempaccount.com667a29c2013-04-13 03:39:04 +00001080}
1081
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001082void Context::bindIndexedTransformFeedbackBuffer(GLuint bufferHandle,
1083 GLuint index,
1084 GLintptr offset,
1085 GLsizeiptr size)
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001086{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001087 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001088 mGLState.getCurrentTransformFeedback()->bindIndexedBuffer(index, buffer, offset, size);
shannon.woods%transgaming.com@gtempaccount.com34089352013-04-13 03:36:57 +00001089}
1090
Jiajia Qin6eafb042016-12-27 17:04:07 +08001091void Context::bindGenericAtomicCounterBuffer(GLuint bufferHandle)
1092{
1093 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
1094 mGLState.setGenericAtomicCounterBufferBinding(buffer);
1095}
1096
1097void Context::bindIndexedAtomicCounterBuffer(GLuint bufferHandle,
1098 GLuint index,
1099 GLintptr offset,
1100 GLsizeiptr size)
1101{
1102 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
1103 mGLState.setIndexedAtomicCounterBufferBinding(index, buffer, offset, size);
1104}
1105
Jiajia Qinf546e7d2017-03-27 14:12:59 +08001106void Context::bindGenericShaderStorageBuffer(GLuint bufferHandle)
1107{
1108 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
1109 mGLState.setGenericShaderStorageBufferBinding(buffer);
1110}
1111
1112void Context::bindIndexedShaderStorageBuffer(GLuint bufferHandle,
1113 GLuint index,
1114 GLintptr offset,
1115 GLsizeiptr size)
1116{
1117 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
1118 mGLState.setIndexedShaderStorageBufferBinding(index, buffer, offset, size);
1119}
1120
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001121void Context::bindCopyReadBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +00001122{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001123 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001124 mGLState.setCopyReadBufferBinding(buffer);
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +00001125}
1126
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001127void Context::bindCopyWriteBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +00001128{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001129 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001130 mGLState.setCopyWriteBufferBinding(buffer);
shannon.woods%transgaming.com@gtempaccount.com51171882013-04-13 03:39:10 +00001131}
1132
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001133void Context::bindPixelPackBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001134{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001135 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001136 mGLState.setPixelPackBufferBinding(buffer);
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001137}
1138
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001139void Context::bindPixelUnpackBuffer(GLuint bufferHandle)
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001140{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001141 Buffer *buffer = mState.mBuffers->checkBufferAllocation(mImplementation.get(), bufferHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001142 mGLState.setPixelUnpackBufferBinding(buffer);
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001143}
1144
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001145void Context::useProgram(GLuint program)
1146{
Jamie Madill6c1f6712017-02-14 19:08:04 -05001147 mGLState.setProgram(this, getProgram(program));
daniel@transgaming.com95d29422012-07-24 18:36:10 +00001148}
1149
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001150void Context::bindTransformFeedback(GLuint transformFeedbackHandle)
Geoff Langc8058452014-02-03 12:04:11 -05001151{
Jamie Madill3f01e6c2016-03-08 13:53:02 -05001152 TransformFeedback *transformFeedback =
1153 checkTransformFeedbackAllocation(transformFeedbackHandle);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001154 mGLState.setTransformFeedbackBinding(transformFeedback);
Geoff Langc8058452014-02-03 12:04:11 -05001155}
1156
Geoff Lang5aad9672014-09-08 11:10:42 -04001157Error Context::beginQuery(GLenum target, GLuint query)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001158{
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001159 Query *queryObject = getQuery(query, true, target);
Jamie Madilldb2f14c2014-05-13 13:56:30 -04001160 ASSERT(queryObject);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001161
Geoff Lang5aad9672014-09-08 11:10:42 -04001162 // begin query
1163 Error error = queryObject->begin();
1164 if (error.isError())
1165 {
1166 return error;
1167 }
1168
1169 // set query as active for specified target only if begin succeeded
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001170 mGLState.setActiveQuery(target, queryObject);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001171
He Yunchaoacd18982017-01-04 10:46:42 +08001172 return NoError();
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001173}
1174
Geoff Lang5aad9672014-09-08 11:10:42 -04001175Error Context::endQuery(GLenum target)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001176{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001177 Query *queryObject = mGLState.getActiveQuery(target);
Jamie Madill45c785d2014-05-13 14:09:34 -04001178 ASSERT(queryObject);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001179
Geoff Lang5aad9672014-09-08 11:10:42 -04001180 gl::Error error = queryObject->end();
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001181
Geoff Lang5aad9672014-09-08 11:10:42 -04001182 // Always unbind the query, even if there was an error. This may delete the query object.
Yunchao Hef81ce4a2017-04-24 10:49:17 +08001183 mGLState.setActiveQuery(target, nullptr);
Geoff Lang5aad9672014-09-08 11:10:42 -04001184
1185 return error;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001186}
1187
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001188Error Context::queryCounter(GLuint id, GLenum target)
1189{
1190 ASSERT(target == GL_TIMESTAMP_EXT);
1191
1192 Query *queryObject = getQuery(id, true, target);
1193 ASSERT(queryObject);
1194
1195 return queryObject->queryCounter();
1196}
1197
1198void Context::getQueryiv(GLenum target, GLenum pname, GLint *params)
1199{
1200 switch (pname)
1201 {
1202 case GL_CURRENT_QUERY_EXT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001203 params[0] = mGLState.getActiveQueryId(target);
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001204 break;
1205 case GL_QUERY_COUNTER_BITS_EXT:
1206 switch (target)
1207 {
1208 case GL_TIME_ELAPSED_EXT:
1209 params[0] = getExtensions().queryCounterBitsTimeElapsed;
1210 break;
1211 case GL_TIMESTAMP_EXT:
1212 params[0] = getExtensions().queryCounterBitsTimestamp;
1213 break;
1214 default:
1215 UNREACHABLE();
1216 params[0] = 0;
1217 break;
1218 }
1219 break;
1220 default:
1221 UNREACHABLE();
1222 return;
1223 }
1224}
1225
Geoff Lang2186c382016-10-14 10:54:54 -04001226void Context::getQueryObjectiv(GLuint id, GLenum pname, GLint *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001227{
Geoff Lang2186c382016-10-14 10:54:54 -04001228 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001229}
1230
Geoff Lang2186c382016-10-14 10:54:54 -04001231void Context::getQueryObjectuiv(GLuint id, GLenum pname, GLuint *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001232{
Geoff Lang2186c382016-10-14 10:54:54 -04001233 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001234}
1235
Geoff Lang2186c382016-10-14 10:54:54 -04001236void Context::getQueryObjecti64v(GLuint id, GLenum pname, GLint64 *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001237{
Geoff Lang2186c382016-10-14 10:54:54 -04001238 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001239}
1240
Geoff Lang2186c382016-10-14 10:54:54 -04001241void Context::getQueryObjectui64v(GLuint id, GLenum pname, GLuint64 *params)
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001242{
Geoff Lang2186c382016-10-14 10:54:54 -04001243 handleError(GetQueryObjectParameter(getQuery(id), pname, params));
Ian Ewell3ffd78b2016-01-22 16:09:42 -05001244}
1245
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05001246Framebuffer *Context::getFramebuffer(GLuint handle) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001247{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05001248 return mState.mFramebuffers->getFramebuffer(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001249}
1250
Jamie Madill2f348d22017-06-05 10:50:59 -04001251FenceNV *Context::getFenceNV(GLuint handle)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001252{
Jamie Madill4e25a0d2016-03-08 13:53:03 -05001253 auto fence = mFenceNVMap.find(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001254
Jamie Madill33dc8432013-07-26 11:55:05 -04001255 if (fence == mFenceNVMap.end())
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001256 {
Yunchao Hef81ce4a2017-04-24 10:49:17 +08001257 return nullptr;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001258 }
1259 else
1260 {
1261 return fence->second;
1262 }
1263}
1264
Jamie Madill2f348d22017-06-05 10:50:59 -04001265Query *Context::getQuery(GLuint handle, bool create, GLenum type)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001266{
Jamie Madill4e25a0d2016-03-08 13:53:03 -05001267 auto query = mQueryMap.find(handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001268
1269 if (query == mQueryMap.end())
1270 {
Yunchao Hef81ce4a2017-04-24 10:49:17 +08001271 return nullptr;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001272 }
1273 else
1274 {
1275 if (!query->second && create)
1276 {
Jamie Madill53ea9cc2016-05-17 10:12:52 -04001277 query->second = new Query(mImplementation->createQuery(type), handle);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001278 query->second->addRef();
1279 }
1280 return query->second;
1281 }
1282}
1283
Geoff Lang70d0f492015-12-10 17:45:46 -05001284Query *Context::getQuery(GLuint handle) const
1285{
1286 auto iter = mQueryMap.find(handle);
1287 return (iter != mQueryMap.end()) ? iter->second : nullptr;
1288}
1289
Jamie Madill1fc7e2c2014-01-21 16:47:10 -05001290Texture *Context::getTargetTexture(GLenum target) const
1291{
Ian Ewellbda75592016-04-18 17:25:54 -04001292 ASSERT(ValidTextureTarget(this, target) || ValidTextureExternalTarget(this, target));
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001293 return mGLState.getTargetTexture(target);
shannon.woods%transgaming.com@gtempaccount.comc926e5f2013-04-13 03:39:18 +00001294}
1295
Geoff Lang76b10c92014-09-05 16:28:14 -04001296Texture *Context::getSamplerTexture(unsigned int sampler, GLenum type) const
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001297{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001298 return mGLState.getSamplerTexture(sampler, type);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001299}
1300
Geoff Lang492a7e42014-11-05 13:27:06 -05001301Compiler *Context::getCompiler() const
1302{
Jamie Madill2f348d22017-06-05 10:50:59 -04001303 if (mCompiler.get() == nullptr)
1304 {
1305 mCompiler.set(new Compiler(mImplementation.get(), mState));
1306 }
1307 return mCompiler.get();
Geoff Lang492a7e42014-11-05 13:27:06 -05001308}
1309
Jamie Madillc1d770e2017-04-13 17:31:24 -04001310void Context::getBooleanvImpl(GLenum pname, GLboolean *params)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001311{
1312 switch (pname)
1313 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001314 case GL_SHADER_COMPILER:
1315 *params = GL_TRUE;
1316 break;
1317 case GL_CONTEXT_ROBUST_ACCESS_EXT:
1318 *params = mRobustAccess ? GL_TRUE : GL_FALSE;
1319 break;
1320 default:
1321 mGLState.getBooleanv(pname, params);
1322 break;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001323 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001324}
1325
Jamie Madillc1d770e2017-04-13 17:31:24 -04001326void Context::getFloatvImpl(GLenum pname, GLfloat *params)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001327{
Shannon Woods53a94a82014-06-24 15:20:36 -04001328 // Queries about context capabilities and maximums are answered by Context.
1329 // Queries about current GL state values are answered by State.
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001330 switch (pname)
1331 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001332 case GL_ALIASED_LINE_WIDTH_RANGE:
1333 params[0] = mCaps.minAliasedLineWidth;
1334 params[1] = mCaps.maxAliasedLineWidth;
1335 break;
1336 case GL_ALIASED_POINT_SIZE_RANGE:
1337 params[0] = mCaps.minAliasedPointSize;
1338 params[1] = mCaps.maxAliasedPointSize;
1339 break;
1340 case GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT:
1341 ASSERT(mExtensions.textureFilterAnisotropic);
1342 *params = mExtensions.maxTextureAnisotropy;
1343 break;
1344 case GL_MAX_TEXTURE_LOD_BIAS:
1345 *params = mCaps.maxLODBias;
1346 break;
1347
1348 case GL_PATH_MODELVIEW_MATRIX_CHROMIUM:
1349 case GL_PATH_PROJECTION_MATRIX_CHROMIUM:
1350 {
1351 ASSERT(mExtensions.pathRendering);
1352 const GLfloat *m = mGLState.getPathRenderingMatrix(pname);
1353 memcpy(params, m, 16 * sizeof(GLfloat));
1354 }
Geoff Lange6d4e122015-06-29 13:33:55 -04001355 break;
Sami Väisänene45e53b2016-05-25 10:36:04 +03001356
Jamie Madill231c7f52017-04-26 13:45:37 -04001357 default:
1358 mGLState.getFloatv(pname, params);
1359 break;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001360 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001361}
1362
Jamie Madillc1d770e2017-04-13 17:31:24 -04001363void Context::getIntegervImpl(GLenum pname, GLint *params)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001364{
Shannon Woods53a94a82014-06-24 15:20:36 -04001365 // Queries about context capabilities and maximums are answered by Context.
1366 // Queries about current GL state values are answered by State.
shannon.woods%transgaming.com@gtempaccount.combc373e52013-04-13 03:31:23 +00001367
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001368 switch (pname)
1369 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001370 case GL_MAX_VERTEX_ATTRIBS:
1371 *params = mCaps.maxVertexAttributes;
1372 break;
1373 case GL_MAX_VERTEX_UNIFORM_VECTORS:
1374 *params = mCaps.maxVertexUniformVectors;
1375 break;
1376 case GL_MAX_VERTEX_UNIFORM_COMPONENTS:
1377 *params = mCaps.maxVertexUniformComponents;
1378 break;
1379 case GL_MAX_VARYING_VECTORS:
1380 *params = mCaps.maxVaryingVectors;
1381 break;
1382 case GL_MAX_VARYING_COMPONENTS:
1383 *params = mCaps.maxVertexOutputComponents;
1384 break;
1385 case GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS:
1386 *params = mCaps.maxCombinedTextureImageUnits;
1387 break;
1388 case GL_MAX_VERTEX_TEXTURE_IMAGE_UNITS:
1389 *params = mCaps.maxVertexTextureImageUnits;
1390 break;
1391 case GL_MAX_TEXTURE_IMAGE_UNITS:
1392 *params = mCaps.maxTextureImageUnits;
1393 break;
1394 case GL_MAX_FRAGMENT_UNIFORM_VECTORS:
1395 *params = mCaps.maxFragmentUniformVectors;
1396 break;
1397 case GL_MAX_FRAGMENT_UNIFORM_COMPONENTS:
1398 *params = mCaps.maxFragmentUniformComponents;
1399 break;
1400 case GL_MAX_RENDERBUFFER_SIZE:
1401 *params = mCaps.maxRenderbufferSize;
1402 break;
1403 case GL_MAX_COLOR_ATTACHMENTS_EXT:
1404 *params = mCaps.maxColorAttachments;
1405 break;
1406 case GL_MAX_DRAW_BUFFERS_EXT:
1407 *params = mCaps.maxDrawBuffers;
1408 break;
1409 // case GL_FRAMEBUFFER_BINDING: // now equivalent to
1410 // GL_DRAW_FRAMEBUFFER_BINDING_ANGLE
1411 case GL_SUBPIXEL_BITS:
1412 *params = 4;
1413 break;
1414 case GL_MAX_TEXTURE_SIZE:
1415 *params = mCaps.max2DTextureSize;
1416 break;
1417 case GL_MAX_CUBE_MAP_TEXTURE_SIZE:
1418 *params = mCaps.maxCubeMapTextureSize;
1419 break;
1420 case GL_MAX_3D_TEXTURE_SIZE:
1421 *params = mCaps.max3DTextureSize;
1422 break;
1423 case GL_MAX_ARRAY_TEXTURE_LAYERS:
1424 *params = mCaps.maxArrayTextureLayers;
1425 break;
1426 case GL_UNIFORM_BUFFER_OFFSET_ALIGNMENT:
1427 *params = mCaps.uniformBufferOffsetAlignment;
1428 break;
1429 case GL_MAX_UNIFORM_BUFFER_BINDINGS:
1430 *params = mCaps.maxUniformBufferBindings;
1431 break;
1432 case GL_MAX_VERTEX_UNIFORM_BLOCKS:
1433 *params = mCaps.maxVertexUniformBlocks;
1434 break;
1435 case GL_MAX_FRAGMENT_UNIFORM_BLOCKS:
1436 *params = mCaps.maxFragmentUniformBlocks;
1437 break;
1438 case GL_MAX_COMBINED_UNIFORM_BLOCKS:
1439 *params = mCaps.maxCombinedTextureImageUnits;
1440 break;
1441 case GL_MAX_VERTEX_OUTPUT_COMPONENTS:
1442 *params = mCaps.maxVertexOutputComponents;
1443 break;
1444 case GL_MAX_FRAGMENT_INPUT_COMPONENTS:
1445 *params = mCaps.maxFragmentInputComponents;
1446 break;
1447 case GL_MIN_PROGRAM_TEXEL_OFFSET:
1448 *params = mCaps.minProgramTexelOffset;
1449 break;
1450 case GL_MAX_PROGRAM_TEXEL_OFFSET:
1451 *params = mCaps.maxProgramTexelOffset;
1452 break;
1453 case GL_MAJOR_VERSION:
1454 *params = getClientVersion().major;
1455 break;
1456 case GL_MINOR_VERSION:
1457 *params = getClientVersion().minor;
1458 break;
1459 case GL_MAX_ELEMENTS_INDICES:
1460 *params = mCaps.maxElementsIndices;
1461 break;
1462 case GL_MAX_ELEMENTS_VERTICES:
1463 *params = mCaps.maxElementsVertices;
1464 break;
1465 case GL_MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS:
1466 *params = mCaps.maxTransformFeedbackInterleavedComponents;
1467 break;
1468 case GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_ATTRIBS:
1469 *params = mCaps.maxTransformFeedbackSeparateAttributes;
1470 break;
1471 case GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_COMPONENTS:
1472 *params = mCaps.maxTransformFeedbackSeparateComponents;
1473 break;
1474 case GL_NUM_COMPRESSED_TEXTURE_FORMATS:
1475 *params = static_cast<GLint>(mCaps.compressedTextureFormats.size());
1476 break;
1477 case GL_MAX_SAMPLES_ANGLE:
1478 *params = mCaps.maxSamples;
1479 break;
1480 case GL_MAX_VIEWPORT_DIMS:
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001481 {
Geoff Langc0b9ef42014-07-02 10:02:37 -04001482 params[0] = mCaps.maxViewportWidth;
1483 params[1] = mCaps.maxViewportHeight;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001484 }
1485 break;
Jamie Madill231c7f52017-04-26 13:45:37 -04001486 case GL_COMPRESSED_TEXTURE_FORMATS:
1487 std::copy(mCaps.compressedTextureFormats.begin(), mCaps.compressedTextureFormats.end(),
1488 params);
1489 break;
1490 case GL_RESET_NOTIFICATION_STRATEGY_EXT:
1491 *params = mResetStrategy;
1492 break;
1493 case GL_NUM_SHADER_BINARY_FORMATS:
1494 *params = static_cast<GLint>(mCaps.shaderBinaryFormats.size());
1495 break;
1496 case GL_SHADER_BINARY_FORMATS:
1497 std::copy(mCaps.shaderBinaryFormats.begin(), mCaps.shaderBinaryFormats.end(), params);
1498 break;
1499 case GL_NUM_PROGRAM_BINARY_FORMATS:
1500 *params = static_cast<GLint>(mCaps.programBinaryFormats.size());
1501 break;
1502 case GL_PROGRAM_BINARY_FORMATS:
1503 std::copy(mCaps.programBinaryFormats.begin(), mCaps.programBinaryFormats.end(), params);
1504 break;
1505 case GL_NUM_EXTENSIONS:
1506 *params = static_cast<GLint>(mExtensionStrings.size());
1507 break;
Geoff Lang70d0f492015-12-10 17:45:46 -05001508
Jamie Madill231c7f52017-04-26 13:45:37 -04001509 // GL_KHR_debug
1510 case GL_MAX_DEBUG_MESSAGE_LENGTH:
1511 *params = mExtensions.maxDebugMessageLength;
1512 break;
1513 case GL_MAX_DEBUG_LOGGED_MESSAGES:
1514 *params = mExtensions.maxDebugLoggedMessages;
1515 break;
1516 case GL_MAX_DEBUG_GROUP_STACK_DEPTH:
1517 *params = mExtensions.maxDebugGroupStackDepth;
1518 break;
1519 case GL_MAX_LABEL_LENGTH:
1520 *params = mExtensions.maxLabelLength;
1521 break;
Geoff Lang70d0f492015-12-10 17:45:46 -05001522
Jamie Madill231c7f52017-04-26 13:45:37 -04001523 // GL_EXT_disjoint_timer_query
1524 case GL_GPU_DISJOINT_EXT:
1525 *params = mImplementation->getGPUDisjoint();
1526 break;
1527 case GL_MAX_FRAMEBUFFER_WIDTH:
1528 *params = mCaps.maxFramebufferWidth;
1529 break;
1530 case GL_MAX_FRAMEBUFFER_HEIGHT:
1531 *params = mCaps.maxFramebufferHeight;
1532 break;
1533 case GL_MAX_FRAMEBUFFER_SAMPLES:
1534 *params = mCaps.maxFramebufferSamples;
1535 break;
1536 case GL_MAX_SAMPLE_MASK_WORDS:
1537 *params = mCaps.maxSampleMaskWords;
1538 break;
1539 case GL_MAX_COLOR_TEXTURE_SAMPLES:
1540 *params = mCaps.maxColorTextureSamples;
1541 break;
1542 case GL_MAX_DEPTH_TEXTURE_SAMPLES:
1543 *params = mCaps.maxDepthTextureSamples;
1544 break;
1545 case GL_MAX_INTEGER_SAMPLES:
1546 *params = mCaps.maxIntegerSamples;
1547 break;
1548 case GL_MAX_VERTEX_ATTRIB_RELATIVE_OFFSET:
1549 *params = mCaps.maxVertexAttribRelativeOffset;
1550 break;
1551 case GL_MAX_VERTEX_ATTRIB_BINDINGS:
1552 *params = mCaps.maxVertexAttribBindings;
1553 break;
1554 case GL_MAX_VERTEX_ATTRIB_STRIDE:
1555 *params = mCaps.maxVertexAttribStride;
1556 break;
1557 case GL_MAX_VERTEX_ATOMIC_COUNTER_BUFFERS:
1558 *params = mCaps.maxVertexAtomicCounterBuffers;
1559 break;
1560 case GL_MAX_VERTEX_ATOMIC_COUNTERS:
1561 *params = mCaps.maxVertexAtomicCounters;
1562 break;
1563 case GL_MAX_VERTEX_IMAGE_UNIFORMS:
1564 *params = mCaps.maxVertexImageUniforms;
1565 break;
1566 case GL_MAX_VERTEX_SHADER_STORAGE_BLOCKS:
1567 *params = mCaps.maxVertexShaderStorageBlocks;
1568 break;
1569 case GL_MAX_FRAGMENT_ATOMIC_COUNTER_BUFFERS:
1570 *params = mCaps.maxFragmentAtomicCounterBuffers;
1571 break;
1572 case GL_MAX_FRAGMENT_ATOMIC_COUNTERS:
1573 *params = mCaps.maxFragmentAtomicCounters;
1574 break;
1575 case GL_MAX_FRAGMENT_IMAGE_UNIFORMS:
1576 *params = mCaps.maxFragmentImageUniforms;
1577 break;
1578 case GL_MAX_FRAGMENT_SHADER_STORAGE_BLOCKS:
1579 *params = mCaps.maxFragmentShaderStorageBlocks;
1580 break;
1581 case GL_MIN_PROGRAM_TEXTURE_GATHER_OFFSET:
1582 *params = mCaps.minProgramTextureGatherOffset;
1583 break;
1584 case GL_MAX_PROGRAM_TEXTURE_GATHER_OFFSET:
1585 *params = mCaps.maxProgramTextureGatherOffset;
1586 break;
1587 case GL_MAX_COMPUTE_WORK_GROUP_INVOCATIONS:
1588 *params = mCaps.maxComputeWorkGroupInvocations;
1589 break;
1590 case GL_MAX_COMPUTE_UNIFORM_BLOCKS:
1591 *params = mCaps.maxComputeUniformBlocks;
1592 break;
1593 case GL_MAX_COMPUTE_TEXTURE_IMAGE_UNITS:
1594 *params = mCaps.maxComputeTextureImageUnits;
1595 break;
1596 case GL_MAX_COMPUTE_SHARED_MEMORY_SIZE:
1597 *params = mCaps.maxComputeSharedMemorySize;
1598 break;
1599 case GL_MAX_COMPUTE_UNIFORM_COMPONENTS:
1600 *params = mCaps.maxComputeUniformComponents;
1601 break;
1602 case GL_MAX_COMPUTE_ATOMIC_COUNTER_BUFFERS:
1603 *params = mCaps.maxComputeAtomicCounterBuffers;
1604 break;
1605 case GL_MAX_COMPUTE_ATOMIC_COUNTERS:
1606 *params = mCaps.maxComputeAtomicCounters;
1607 break;
1608 case GL_MAX_COMPUTE_IMAGE_UNIFORMS:
1609 *params = mCaps.maxComputeImageUniforms;
1610 break;
1611 case GL_MAX_COMBINED_COMPUTE_UNIFORM_COMPONENTS:
1612 *params = mCaps.maxCombinedComputeUniformComponents;
1613 break;
1614 case GL_MAX_COMPUTE_SHADER_STORAGE_BLOCKS:
1615 *params = mCaps.maxComputeShaderStorageBlocks;
1616 break;
1617 case GL_MAX_COMBINED_SHADER_OUTPUT_RESOURCES:
1618 *params = mCaps.maxCombinedShaderOutputResources;
1619 break;
1620 case GL_MAX_UNIFORM_LOCATIONS:
1621 *params = mCaps.maxUniformLocations;
1622 break;
1623 case GL_MAX_ATOMIC_COUNTER_BUFFER_BINDINGS:
1624 *params = mCaps.maxAtomicCounterBufferBindings;
1625 break;
1626 case GL_MAX_ATOMIC_COUNTER_BUFFER_SIZE:
1627 *params = mCaps.maxAtomicCounterBufferSize;
1628 break;
1629 case GL_MAX_COMBINED_ATOMIC_COUNTER_BUFFERS:
1630 *params = mCaps.maxCombinedAtomicCounterBuffers;
1631 break;
1632 case GL_MAX_COMBINED_ATOMIC_COUNTERS:
1633 *params = mCaps.maxCombinedAtomicCounters;
1634 break;
1635 case GL_MAX_IMAGE_UNITS:
1636 *params = mCaps.maxImageUnits;
1637 break;
1638 case GL_MAX_COMBINED_IMAGE_UNIFORMS:
1639 *params = mCaps.maxCombinedImageUniforms;
1640 break;
1641 case GL_MAX_SHADER_STORAGE_BUFFER_BINDINGS:
1642 *params = mCaps.maxShaderStorageBufferBindings;
1643 break;
1644 case GL_MAX_COMBINED_SHADER_STORAGE_BLOCKS:
1645 *params = mCaps.maxCombinedShaderStorageBlocks;
1646 break;
1647 case GL_SHADER_STORAGE_BUFFER_OFFSET_ALIGNMENT:
1648 *params = mCaps.shaderStorageBufferOffsetAlignment;
1649 break;
1650 default:
1651 mGLState.getIntegerv(this, pname, params);
1652 break;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001653 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001654}
1655
Jamie Madill893ab082014-05-16 16:56:10 -04001656void Context::getInteger64v(GLenum pname, GLint64 *params)
Jamie Madill0fda9862013-07-19 16:36:55 -04001657{
Shannon Woods53a94a82014-06-24 15:20:36 -04001658 // Queries about context capabilities and maximums are answered by Context.
1659 // Queries about current GL state values are answered by State.
Jamie Madill0fda9862013-07-19 16:36:55 -04001660 switch (pname)
1661 {
Jamie Madill231c7f52017-04-26 13:45:37 -04001662 case GL_MAX_ELEMENT_INDEX:
1663 *params = mCaps.maxElementIndex;
1664 break;
1665 case GL_MAX_UNIFORM_BLOCK_SIZE:
1666 *params = mCaps.maxUniformBlockSize;
1667 break;
1668 case GL_MAX_COMBINED_VERTEX_UNIFORM_COMPONENTS:
1669 *params = mCaps.maxCombinedVertexUniformComponents;
1670 break;
1671 case GL_MAX_COMBINED_FRAGMENT_UNIFORM_COMPONENTS:
1672 *params = mCaps.maxCombinedFragmentUniformComponents;
1673 break;
1674 case GL_MAX_SERVER_WAIT_TIMEOUT:
1675 *params = mCaps.maxServerWaitTimeout;
1676 break;
Ian Ewell53f59f42016-01-28 17:36:55 -05001677
Jamie Madill231c7f52017-04-26 13:45:37 -04001678 // GL_EXT_disjoint_timer_query
1679 case GL_TIMESTAMP_EXT:
1680 *params = mImplementation->getTimestamp();
1681 break;
Martin Radev66fb8202016-07-28 11:45:20 +03001682
Jamie Madill231c7f52017-04-26 13:45:37 -04001683 case GL_MAX_SHADER_STORAGE_BLOCK_SIZE:
1684 *params = mCaps.maxShaderStorageBlockSize;
1685 break;
1686 default:
1687 UNREACHABLE();
1688 break;
Jamie Madill0fda9862013-07-19 16:36:55 -04001689 }
Jamie Madill0fda9862013-07-19 16:36:55 -04001690}
1691
Geoff Lang70d0f492015-12-10 17:45:46 -05001692void Context::getPointerv(GLenum pname, void **params) const
1693{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001694 mGLState.getPointerv(pname, params);
Geoff Lang70d0f492015-12-10 17:45:46 -05001695}
1696
Martin Radev66fb8202016-07-28 11:45:20 +03001697void Context::getIntegeri_v(GLenum target, GLuint index, GLint *data)
Shannon Woods1b2fb852013-08-19 14:28:48 -04001698{
Shannon Woods53a94a82014-06-24 15:20:36 -04001699 // Queries about context capabilities and maximums are answered by Context.
1700 // Queries about current GL state values are answered by State.
Martin Radev66fb8202016-07-28 11:45:20 +03001701
1702 GLenum nativeType;
1703 unsigned int numParams;
1704 bool queryStatus = getIndexedQueryParameterInfo(target, &nativeType, &numParams);
1705 ASSERT(queryStatus);
1706
1707 if (nativeType == GL_INT)
1708 {
1709 switch (target)
1710 {
1711 case GL_MAX_COMPUTE_WORK_GROUP_COUNT:
1712 ASSERT(index < 3u);
1713 *data = mCaps.maxComputeWorkGroupCount[index];
1714 break;
1715 case GL_MAX_COMPUTE_WORK_GROUP_SIZE:
1716 ASSERT(index < 3u);
1717 *data = mCaps.maxComputeWorkGroupSize[index];
1718 break;
1719 default:
1720 mGLState.getIntegeri_v(target, index, data);
1721 }
1722 }
1723 else
1724 {
1725 CastIndexedStateValues(this, nativeType, target, index, numParams, data);
1726 }
Shannon Woods1b2fb852013-08-19 14:28:48 -04001727}
1728
Martin Radev66fb8202016-07-28 11:45:20 +03001729void Context::getInteger64i_v(GLenum target, GLuint index, GLint64 *data)
Shannon Woods1b2fb852013-08-19 14:28:48 -04001730{
Shannon Woods53a94a82014-06-24 15:20:36 -04001731 // Queries about context capabilities and maximums are answered by Context.
1732 // Queries about current GL state values are answered by State.
Martin Radev66fb8202016-07-28 11:45:20 +03001733
1734 GLenum nativeType;
1735 unsigned int numParams;
1736 bool queryStatus = getIndexedQueryParameterInfo(target, &nativeType, &numParams);
1737 ASSERT(queryStatus);
1738
1739 if (nativeType == GL_INT_64_ANGLEX)
1740 {
1741 mGLState.getInteger64i_v(target, index, data);
1742 }
1743 else
1744 {
1745 CastIndexedStateValues(this, nativeType, target, index, numParams, data);
1746 }
1747}
1748
1749void Context::getBooleani_v(GLenum target, GLuint index, GLboolean *data)
1750{
1751 // Queries about context capabilities and maximums are answered by Context.
1752 // Queries about current GL state values are answered by State.
1753
1754 GLenum nativeType;
1755 unsigned int numParams;
1756 bool queryStatus = getIndexedQueryParameterInfo(target, &nativeType, &numParams);
1757 ASSERT(queryStatus);
1758
1759 if (nativeType == GL_BOOL)
1760 {
1761 mGLState.getBooleani_v(target, index, data);
1762 }
1763 else
1764 {
1765 CastIndexedStateValues(this, nativeType, target, index, numParams, data);
1766 }
Shannon Woods1b2fb852013-08-19 14:28:48 -04001767}
1768
He Yunchao010e4db2017-03-03 14:22:06 +08001769void Context::getBufferParameteriv(GLenum target, GLenum pname, GLint *params)
1770{
1771 Buffer *buffer = mGLState.getTargetBuffer(target);
1772 QueryBufferParameteriv(buffer, pname, params);
1773}
1774
1775void Context::getFramebufferAttachmentParameteriv(GLenum target,
1776 GLenum attachment,
1777 GLenum pname,
1778 GLint *params)
1779{
1780 const Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
1781 QueryFramebufferAttachmentParameteriv(framebuffer, attachment, pname, params);
1782}
1783
1784void Context::getRenderbufferParameteriv(GLenum target, GLenum pname, GLint *params)
1785{
1786 Renderbuffer *renderbuffer = mGLState.getCurrentRenderbuffer();
1787 QueryRenderbufferiv(this, renderbuffer, pname, params);
1788}
1789
1790void Context::getTexParameterfv(GLenum target, GLenum pname, GLfloat *params)
1791{
1792 Texture *texture = getTargetTexture(target);
1793 QueryTexParameterfv(texture, pname, params);
1794}
1795
1796void Context::getTexParameteriv(GLenum target, GLenum pname, GLint *params)
1797{
1798 Texture *texture = getTargetTexture(target);
1799 QueryTexParameteriv(texture, pname, params);
1800}
1801void Context::texParameterf(GLenum target, GLenum pname, GLfloat param)
1802{
1803 Texture *texture = getTargetTexture(target);
1804 SetTexParameterf(texture, pname, param);
1805}
1806
1807void Context::texParameterfv(GLenum target, GLenum pname, const GLfloat *params)
1808{
1809 Texture *texture = getTargetTexture(target);
1810 SetTexParameterfv(texture, pname, params);
1811}
1812
1813void Context::texParameteri(GLenum target, GLenum pname, GLint param)
1814{
1815 Texture *texture = getTargetTexture(target);
1816 SetTexParameteri(texture, pname, param);
1817}
1818
1819void Context::texParameteriv(GLenum target, GLenum pname, const GLint *params)
1820{
1821 Texture *texture = getTargetTexture(target);
1822 SetTexParameteriv(texture, pname, params);
1823}
1824
Jamie Madill675fe712016-12-19 13:07:54 -05001825void Context::drawArrays(GLenum mode, GLint first, GLsizei count)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001826{
Jamie Madill1b94d432015-08-07 13:23:23 -04001827 syncRendererState();
Jamie Madillc564c072017-06-01 12:45:42 -04001828 auto error = mImplementation->drawArrays(this, mode, first, count);
Jamie Madill675fe712016-12-19 13:07:54 -05001829 handleError(error);
1830 if (!error.isError())
1831 {
1832 MarkTransformFeedbackBufferUsage(mGLState.getCurrentTransformFeedback());
1833 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001834}
1835
Jamie Madill675fe712016-12-19 13:07:54 -05001836void Context::drawArraysInstanced(GLenum mode, GLint first, GLsizei count, GLsizei instanceCount)
Geoff Langf6db0982015-08-25 13:04:00 -04001837{
1838 syncRendererState();
Jamie Madillc564c072017-06-01 12:45:42 -04001839 auto error = mImplementation->drawArraysInstanced(this, mode, first, count, instanceCount);
Jamie Madill675fe712016-12-19 13:07:54 -05001840 handleError(error);
1841 if (!error.isError())
1842 {
1843 MarkTransformFeedbackBufferUsage(mGLState.getCurrentTransformFeedback());
1844 }
Geoff Langf6db0982015-08-25 13:04:00 -04001845}
1846
Jamie Madill876429b2017-04-20 15:46:24 -04001847void Context::drawElements(GLenum mode, GLsizei count, GLenum type, const void *indices)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001848{
Jamie Madill1b94d432015-08-07 13:23:23 -04001849 syncRendererState();
Jamie Madill9c9b40a2017-04-26 16:31:57 -04001850 const IndexRange &indexRange = getParams<HasIndexRange>().getIndexRange().value();
Jamie Madillc564c072017-06-01 12:45:42 -04001851 handleError(mImplementation->drawElements(this, mode, count, type, indices, indexRange));
Geoff Langf6db0982015-08-25 13:04:00 -04001852}
1853
Jamie Madill675fe712016-12-19 13:07:54 -05001854void Context::drawElementsInstanced(GLenum mode,
1855 GLsizei count,
1856 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04001857 const void *indices,
Jamie Madill9c9b40a2017-04-26 16:31:57 -04001858 GLsizei instances)
Geoff Langf6db0982015-08-25 13:04:00 -04001859{
1860 syncRendererState();
Jamie Madill9c9b40a2017-04-26 16:31:57 -04001861 const IndexRange &indexRange = getParams<HasIndexRange>().getIndexRange().value();
Jamie Madillc564c072017-06-01 12:45:42 -04001862 handleError(mImplementation->drawElementsInstanced(this, mode, count, type, indices, instances,
1863 indexRange));
Geoff Langf6db0982015-08-25 13:04:00 -04001864}
1865
Jamie Madill675fe712016-12-19 13:07:54 -05001866void Context::drawRangeElements(GLenum mode,
1867 GLuint start,
1868 GLuint end,
1869 GLsizei count,
1870 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04001871 const void *indices)
Geoff Langf6db0982015-08-25 13:04:00 -04001872{
1873 syncRendererState();
Jamie Madill9c9b40a2017-04-26 16:31:57 -04001874 const IndexRange &indexRange = getParams<HasIndexRange>().getIndexRange().value();
Jamie Madillc564c072017-06-01 12:45:42 -04001875 handleError(mImplementation->drawRangeElements(this, mode, start, end, count, type, indices,
1876 indexRange));
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001877}
1878
Jamie Madill876429b2017-04-20 15:46:24 -04001879void Context::drawArraysIndirect(GLenum mode, const void *indirect)
Jiajia Qind9671222016-11-29 16:30:31 +08001880{
1881 syncRendererState();
Jamie Madillc564c072017-06-01 12:45:42 -04001882 handleError(mImplementation->drawArraysIndirect(this, mode, indirect));
Jiajia Qind9671222016-11-29 16:30:31 +08001883}
1884
Jamie Madill876429b2017-04-20 15:46:24 -04001885void Context::drawElementsIndirect(GLenum mode, GLenum type, const void *indirect)
Jiajia Qind9671222016-11-29 16:30:31 +08001886{
1887 syncRendererState();
Jamie Madillc564c072017-06-01 12:45:42 -04001888 handleError(mImplementation->drawElementsIndirect(this, mode, type, indirect));
Jiajia Qind9671222016-11-29 16:30:31 +08001889}
1890
Jamie Madill675fe712016-12-19 13:07:54 -05001891void Context::flush()
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001892{
Jamie Madill675fe712016-12-19 13:07:54 -05001893 handleError(mImplementation->flush());
Geoff Lang129753a2015-01-09 16:52:09 -05001894}
1895
Jamie Madill675fe712016-12-19 13:07:54 -05001896void Context::finish()
Geoff Lang129753a2015-01-09 16:52:09 -05001897{
Jamie Madill675fe712016-12-19 13:07:54 -05001898 handleError(mImplementation->finish());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00001899}
1900
Austin Kinross6ee1e782015-05-29 17:05:37 -07001901void Context::insertEventMarker(GLsizei length, const char *marker)
1902{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04001903 ASSERT(mImplementation);
1904 mImplementation->insertEventMarker(length, marker);
Austin Kinross6ee1e782015-05-29 17:05:37 -07001905}
1906
1907void Context::pushGroupMarker(GLsizei length, const char *marker)
1908{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04001909 ASSERT(mImplementation);
1910 mImplementation->pushGroupMarker(length, marker);
Austin Kinross6ee1e782015-05-29 17:05:37 -07001911}
1912
1913void Context::popGroupMarker()
1914{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04001915 ASSERT(mImplementation);
1916 mImplementation->popGroupMarker();
Austin Kinross6ee1e782015-05-29 17:05:37 -07001917}
1918
Geoff Langd8605522016-04-13 10:19:12 -04001919void Context::bindUniformLocation(GLuint program, GLint location, const GLchar *name)
1920{
1921 Program *programObject = getProgram(program);
1922 ASSERT(programObject);
1923
1924 programObject->bindUniformLocation(location, name);
1925}
1926
Sami Väisänena797e062016-05-12 15:23:40 +03001927void Context::setCoverageModulation(GLenum components)
1928{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07001929 mGLState.setCoverageModulation(components);
Sami Väisänena797e062016-05-12 15:23:40 +03001930}
1931
Sami Väisänene45e53b2016-05-25 10:36:04 +03001932void Context::loadPathRenderingMatrix(GLenum matrixMode, const GLfloat *matrix)
1933{
1934 mGLState.loadPathRenderingMatrix(matrixMode, matrix);
1935}
1936
1937void Context::loadPathRenderingIdentityMatrix(GLenum matrixMode)
1938{
1939 GLfloat I[16];
1940 angle::Matrix<GLfloat>::setToIdentity(I);
1941
1942 mGLState.loadPathRenderingMatrix(matrixMode, I);
1943}
1944
1945void Context::stencilFillPath(GLuint path, GLenum fillMode, GLuint mask)
1946{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001947 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001948 if (!pathObj)
1949 return;
1950
1951 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1952 syncRendererState();
1953
1954 mImplementation->stencilFillPath(pathObj, fillMode, mask);
1955}
1956
1957void Context::stencilStrokePath(GLuint path, GLint reference, GLuint mask)
1958{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001959 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001960 if (!pathObj)
1961 return;
1962
1963 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1964 syncRendererState();
1965
1966 mImplementation->stencilStrokePath(pathObj, reference, mask);
1967}
1968
1969void Context::coverFillPath(GLuint path, GLenum coverMode)
1970{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001971 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001972 if (!pathObj)
1973 return;
1974
1975 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1976 syncRendererState();
1977
1978 mImplementation->coverFillPath(pathObj, coverMode);
1979}
1980
1981void Context::coverStrokePath(GLuint path, GLenum coverMode)
1982{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001983 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001984 if (!pathObj)
1985 return;
1986
1987 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
1988 syncRendererState();
1989
1990 mImplementation->coverStrokePath(pathObj, coverMode);
1991}
1992
1993void Context::stencilThenCoverFillPath(GLuint path, GLenum fillMode, GLuint mask, GLenum coverMode)
1994{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05001995 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03001996 if (!pathObj)
1997 return;
1998
1999 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2000 syncRendererState();
2001
2002 mImplementation->stencilThenCoverFillPath(pathObj, fillMode, mask, coverMode);
2003}
2004
2005void Context::stencilThenCoverStrokePath(GLuint path,
2006 GLint reference,
2007 GLuint mask,
2008 GLenum coverMode)
2009{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002010 const auto *pathObj = mState.mPaths->getPath(path);
Sami Väisänene45e53b2016-05-25 10:36:04 +03002011 if (!pathObj)
2012 return;
2013
2014 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2015 syncRendererState();
2016
2017 mImplementation->stencilThenCoverStrokePath(pathObj, reference, mask, coverMode);
2018}
2019
Sami Väisänend59ca052016-06-21 16:10:00 +03002020void Context::coverFillPathInstanced(GLsizei numPaths,
2021 GLenum pathNameType,
2022 const void *paths,
2023 GLuint pathBase,
2024 GLenum coverMode,
2025 GLenum transformType,
2026 const GLfloat *transformValues)
2027{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002028 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002029
2030 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2031 syncRendererState();
2032
2033 mImplementation->coverFillPathInstanced(pathObjects, coverMode, transformType, transformValues);
2034}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002035
Sami Väisänend59ca052016-06-21 16:10:00 +03002036void Context::coverStrokePathInstanced(GLsizei numPaths,
2037 GLenum pathNameType,
2038 const void *paths,
2039 GLuint pathBase,
2040 GLenum coverMode,
2041 GLenum transformType,
2042 const GLfloat *transformValues)
2043{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002044 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002045
2046 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2047 syncRendererState();
2048
2049 mImplementation->coverStrokePathInstanced(pathObjects, coverMode, transformType,
2050 transformValues);
2051}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002052
Sami Väisänend59ca052016-06-21 16:10:00 +03002053void Context::stencilFillPathInstanced(GLsizei numPaths,
2054 GLenum pathNameType,
2055 const void *paths,
2056 GLuint pathBase,
2057 GLenum fillMode,
2058 GLuint mask,
2059 GLenum transformType,
2060 const GLfloat *transformValues)
2061{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002062 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002063
2064 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2065 syncRendererState();
2066
2067 mImplementation->stencilFillPathInstanced(pathObjects, fillMode, mask, transformType,
2068 transformValues);
2069}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002070
Sami Väisänend59ca052016-06-21 16:10:00 +03002071void Context::stencilStrokePathInstanced(GLsizei numPaths,
2072 GLenum pathNameType,
2073 const void *paths,
2074 GLuint pathBase,
2075 GLint reference,
2076 GLuint mask,
2077 GLenum transformType,
2078 const GLfloat *transformValues)
2079{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002080 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002081
2082 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2083 syncRendererState();
2084
2085 mImplementation->stencilStrokePathInstanced(pathObjects, reference, mask, transformType,
2086 transformValues);
2087}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002088
Sami Väisänend59ca052016-06-21 16:10:00 +03002089void Context::stencilThenCoverFillPathInstanced(GLsizei numPaths,
2090 GLenum pathNameType,
2091 const void *paths,
2092 GLuint pathBase,
2093 GLenum fillMode,
2094 GLuint mask,
2095 GLenum coverMode,
2096 GLenum transformType,
2097 const GLfloat *transformValues)
2098{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002099 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002100
2101 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2102 syncRendererState();
2103
2104 mImplementation->stencilThenCoverFillPathInstanced(pathObjects, coverMode, fillMode, mask,
2105 transformType, transformValues);
2106}
Sami Väisänen46eaa942016-06-29 10:26:37 +03002107
Sami Väisänend59ca052016-06-21 16:10:00 +03002108void Context::stencilThenCoverStrokePathInstanced(GLsizei numPaths,
2109 GLenum pathNameType,
2110 const void *paths,
2111 GLuint pathBase,
2112 GLint reference,
2113 GLuint mask,
2114 GLenum coverMode,
2115 GLenum transformType,
2116 const GLfloat *transformValues)
2117{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002118 const auto &pathObjects = GatherPaths(*mState.mPaths, numPaths, pathNameType, paths, pathBase);
Sami Väisänend59ca052016-06-21 16:10:00 +03002119
2120 // TODO(svaisanen@nvidia.com): maybe sync only state required for path rendering?
2121 syncRendererState();
2122
2123 mImplementation->stencilThenCoverStrokePathInstanced(pathObjects, coverMode, reference, mask,
2124 transformType, transformValues);
2125}
2126
Sami Väisänen46eaa942016-06-29 10:26:37 +03002127void Context::bindFragmentInputLocation(GLuint program, GLint location, const GLchar *name)
2128{
2129 auto *programObject = getProgram(program);
2130
2131 programObject->bindFragmentInputLocation(location, name);
2132}
2133
2134void Context::programPathFragmentInputGen(GLuint program,
2135 GLint location,
2136 GLenum genMode,
2137 GLint components,
2138 const GLfloat *coeffs)
2139{
2140 auto *programObject = getProgram(program);
2141
Jamie Madillbd044ed2017-06-05 12:59:21 -04002142 programObject->pathFragmentInputGen(this, location, genMode, components, coeffs);
Sami Väisänen46eaa942016-06-29 10:26:37 +03002143}
2144
jchen1015015f72017-03-16 13:54:21 +08002145GLuint Context::getProgramResourceIndex(GLuint program, GLenum programInterface, const GLchar *name)
2146{
jchen10fd7c3b52017-03-21 15:36:03 +08002147 const auto *programObject = getProgram(program);
jchen1015015f72017-03-16 13:54:21 +08002148 return QueryProgramResourceIndex(programObject, programInterface, name);
2149}
2150
jchen10fd7c3b52017-03-21 15:36:03 +08002151void Context::getProgramResourceName(GLuint program,
2152 GLenum programInterface,
2153 GLuint index,
2154 GLsizei bufSize,
2155 GLsizei *length,
2156 GLchar *name)
2157{
2158 const auto *programObject = getProgram(program);
2159 QueryProgramResourceName(programObject, programInterface, index, bufSize, length, name);
2160}
2161
Jamie Madill437fa652016-05-03 15:13:24 -04002162void Context::handleError(const Error &error)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002163{
Geoff Langda5777c2014-07-11 09:52:58 -04002164 if (error.isError())
2165 {
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002166 GLenum code = error.getCode();
2167 mErrors.insert(code);
2168 if (code == GL_OUT_OF_MEMORY && getWorkarounds().loseContextOnOutOfMemory)
2169 {
2170 markContextLost();
2171 }
Geoff Lang70d0f492015-12-10 17:45:46 -05002172
2173 if (!error.getMessage().empty())
2174 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002175 auto *debug = &mGLState.getDebug();
2176 debug->insertMessage(GL_DEBUG_SOURCE_API, GL_DEBUG_TYPE_ERROR, error.getID(),
2177 GL_DEBUG_SEVERITY_HIGH, error.getMessage());
Geoff Lang70d0f492015-12-10 17:45:46 -05002178 }
Geoff Langda5777c2014-07-11 09:52:58 -04002179 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002180}
2181
2182// Get one of the recorded errors and clear its flag, if any.
2183// [OpenGL ES 2.0.24] section 2.5 page 13.
2184GLenum Context::getError()
2185{
Geoff Langda5777c2014-07-11 09:52:58 -04002186 if (mErrors.empty())
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002187 {
Geoff Langda5777c2014-07-11 09:52:58 -04002188 return GL_NO_ERROR;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002189 }
Geoff Langda5777c2014-07-11 09:52:58 -04002190 else
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002191 {
Geoff Langda5777c2014-07-11 09:52:58 -04002192 GLenum error = *mErrors.begin();
2193 mErrors.erase(mErrors.begin());
2194 return error;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002195 }
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002196}
2197
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002198// NOTE: this function should not assume that this context is current!
2199void Context::markContextLost()
2200{
2201 if (mResetStrategy == GL_LOSE_CONTEXT_ON_RESET_EXT)
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002202 {
Jamie Madill231c7f52017-04-26 13:45:37 -04002203 mResetStatus = GL_UNKNOWN_CONTEXT_RESET_EXT;
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002204 mContextLostForced = true;
2205 }
Jamie Madill231c7f52017-04-26 13:45:37 -04002206 mContextLost = true;
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002207}
2208
2209bool Context::isContextLost()
2210{
2211 return mContextLost;
2212}
2213
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002214GLenum Context::getResetStatus()
2215{
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002216 // Even if the application doesn't want to know about resets, we want to know
2217 // as it will allow us to skip all the calls.
2218 if (mResetStrategy == GL_NO_RESET_NOTIFICATION_EXT)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002219 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002220 if (!mContextLost && mImplementation->getResetStatus() != GL_NO_ERROR)
Jamie Madill9dd0cf02014-11-24 11:38:51 -05002221 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002222 mContextLost = true;
Jamie Madill9dd0cf02014-11-24 11:38:51 -05002223 }
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002224
2225 // EXT_robustness, section 2.6: If the reset notification behavior is
2226 // NO_RESET_NOTIFICATION_EXT, then the implementation will never deliver notification of
2227 // reset events, and GetGraphicsResetStatusEXT will always return NO_ERROR.
2228 return GL_NO_ERROR;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002229 }
2230
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002231 // The GL_EXT_robustness spec says that if a reset is encountered, a reset
2232 // status should be returned at least once, and GL_NO_ERROR should be returned
2233 // once the device has finished resetting.
2234 if (!mContextLost)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002235 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002236 ASSERT(mResetStatus == GL_NO_ERROR);
2237 mResetStatus = mImplementation->getResetStatus();
shannon.woods@transgaming.comddd6c802013-02-28 23:05:14 +00002238
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002239 if (mResetStatus != GL_NO_ERROR)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002240 {
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002241 mContextLost = true;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002242 }
2243 }
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002244 else if (!mContextLostForced && mResetStatus != GL_NO_ERROR)
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002245 {
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002246 // If markContextLost was used to mark the context lost then
2247 // assume that is not recoverable, and continue to report the
2248 // lost reset status for the lifetime of this context.
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002249 mResetStatus = mImplementation->getResetStatus();
2250 }
Jamie Madill893ab082014-05-16 16:56:10 -04002251
Corentin Wallez87fbe1c2016-08-03 14:41:42 -04002252 return mResetStatus;
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002253}
2254
2255bool Context::isResetNotificationEnabled()
2256{
2257 return (mResetStrategy == GL_LOSE_CONTEXT_ON_RESET_EXT);
2258}
2259
Corentin Walleze3b10e82015-05-20 11:06:25 -04002260const egl::Config *Context::getConfig() const
Régis Fénéon83107972015-02-05 12:57:44 +01002261{
Corentin Walleze3b10e82015-05-20 11:06:25 -04002262 return mConfig;
Régis Fénéon83107972015-02-05 12:57:44 +01002263}
2264
2265EGLenum Context::getClientType() const
2266{
2267 return mClientType;
2268}
2269
2270EGLenum Context::getRenderBuffer() const
2271{
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05002272 const Framebuffer *framebuffer = mState.mFramebuffers->getFramebuffer(0);
2273 if (framebuffer == nullptr)
Corentin Wallez37c39792015-08-20 14:19:46 -04002274 {
2275 return EGL_NONE;
2276 }
Geoff Lang3bf8e3a2016-12-01 17:28:52 -05002277
2278 const FramebufferAttachment *backAttachment = framebuffer->getAttachment(GL_BACK);
2279 ASSERT(backAttachment != nullptr);
2280 return backAttachment->getSurface()->getRenderBuffer();
Régis Fénéon83107972015-02-05 12:57:44 +01002281}
2282
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002283VertexArray *Context::checkVertexArrayAllocation(GLuint vertexArrayHandle)
Geoff Lang36167ab2015-12-07 10:27:14 -05002284{
Jamie Madill5bf9ff42016-02-01 11:13:03 -05002285 // Only called after a prior call to Gen.
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002286 VertexArray *vertexArray = getVertexArray(vertexArrayHandle);
2287 if (!vertexArray)
Geoff Lang36167ab2015-12-07 10:27:14 -05002288 {
Jiawei-Shao2597fb62016-12-09 16:38:02 +08002289 vertexArray = new VertexArray(mImplementation.get(), vertexArrayHandle,
2290 mCaps.maxVertexAttributes, mCaps.maxVertexAttribBindings);
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002291
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002292 mVertexArrayMap[vertexArrayHandle] = vertexArray;
Geoff Lang36167ab2015-12-07 10:27:14 -05002293 }
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002294
2295 return vertexArray;
Geoff Lang36167ab2015-12-07 10:27:14 -05002296}
2297
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002298TransformFeedback *Context::checkTransformFeedbackAllocation(GLuint transformFeedbackHandle)
Geoff Lang36167ab2015-12-07 10:27:14 -05002299{
Jamie Madill5bf9ff42016-02-01 11:13:03 -05002300 // Only called after a prior call to Gen.
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002301 TransformFeedback *transformFeedback = getTransformFeedback(transformFeedbackHandle);
2302 if (!transformFeedback)
Geoff Lang36167ab2015-12-07 10:27:14 -05002303 {
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002304 transformFeedback =
2305 new TransformFeedback(mImplementation.get(), transformFeedbackHandle, mCaps);
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002306 transformFeedback->addRef();
2307 mTransformFeedbackMap[transformFeedbackHandle] = transformFeedback;
Geoff Lang36167ab2015-12-07 10:27:14 -05002308 }
Jamie Madill3f01e6c2016-03-08 13:53:02 -05002309
2310 return transformFeedback;
Geoff Lang36167ab2015-12-07 10:27:14 -05002311}
2312
2313bool Context::isVertexArrayGenerated(GLuint vertexArray)
2314{
Geoff Langf41a7152016-09-19 15:11:17 -04002315 ASSERT(mVertexArrayMap.find(0) != mVertexArrayMap.end());
Geoff Lang36167ab2015-12-07 10:27:14 -05002316 return mVertexArrayMap.find(vertexArray) != mVertexArrayMap.end();
2317}
2318
2319bool Context::isTransformFeedbackGenerated(GLuint transformFeedback)
2320{
Geoff Langf41a7152016-09-19 15:11:17 -04002321 ASSERT(mTransformFeedbackMap.find(0) != mTransformFeedbackMap.end());
Geoff Lang36167ab2015-12-07 10:27:14 -05002322 return mTransformFeedbackMap.find(transformFeedback) != mTransformFeedbackMap.end();
2323}
2324
Shannon Woods53a94a82014-06-24 15:20:36 -04002325void Context::detachTexture(GLuint texture)
2326{
2327 // Simple pass-through to State's detachTexture method, as textures do not require
2328 // allocation map management either here or in the resource manager at detach time.
2329 // Zero textures are held by the Context, and we don't attempt to request them from
2330 // the State.
Jamie Madilla02315b2017-02-23 14:14:47 -05002331 mGLState.detachTexture(this, mZeroTextures, texture);
Shannon Woods53a94a82014-06-24 15:20:36 -04002332}
2333
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002334void Context::detachBuffer(GLuint buffer)
2335{
Yuly Novikov5807a532015-12-03 13:01:22 -05002336 // Simple pass-through to State's detachBuffer method, since
2337 // only buffer attachments to container objects that are bound to the current context
2338 // should be detached. And all those are available in State.
Shannon Woods53a94a82014-06-24 15:20:36 -04002339
Yuly Novikov5807a532015-12-03 13:01:22 -05002340 // [OpenGL ES 3.2] section 5.1.2 page 45:
2341 // Attachments to unbound container objects, such as
2342 // deletion of a buffer attached to a vertex array object which is not bound to the context,
2343 // are not affected and continue to act as references on the deleted object
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002344 mGLState.detachBuffer(buffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002345}
2346
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002347void Context::detachFramebuffer(GLuint framebuffer)
2348{
Shannon Woods53a94a82014-06-24 15:20:36 -04002349 // Framebuffer detachment is handled by Context, because 0 is a valid
2350 // Framebuffer object, and a pointer to it must be passed from Context
2351 // to State at binding time.
2352
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002353 // [OpenGL ES 2.0.24] section 4.4 page 107:
Jamie Madill231c7f52017-04-26 13:45:37 -04002354 // If a framebuffer that is currently bound to the target FRAMEBUFFER is deleted, it is as
2355 // though BindFramebuffer had been executed with the target of FRAMEBUFFER and framebuffer of
2356 // zero.
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002357
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002358 if (mGLState.removeReadFramebufferBinding(framebuffer) && framebuffer != 0)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002359 {
2360 bindReadFramebuffer(0);
2361 }
2362
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002363 if (mGLState.removeDrawFramebufferBinding(framebuffer) && framebuffer != 0)
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002364 {
2365 bindDrawFramebuffer(0);
2366 }
2367}
2368
2369void Context::detachRenderbuffer(GLuint renderbuffer)
2370{
Jamie Madilla02315b2017-02-23 14:14:47 -05002371 mGLState.detachRenderbuffer(this, renderbuffer);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002372}
2373
Jamie Madill57a89722013-07-02 11:57:03 -04002374void Context::detachVertexArray(GLuint vertexArray)
2375{
Jamie Madill77a72f62015-04-14 11:18:32 -04002376 // Vertex array detachment is handled by Context, because 0 is a valid
2377 // VAO, and a pointer to it must be passed from Context to State at
Shannon Woods53a94a82014-06-24 15:20:36 -04002378 // binding time.
2379
Jamie Madill57a89722013-07-02 11:57:03 -04002380 // [OpenGL ES 3.0.2] section 2.10 page 43:
2381 // If a vertex array object that is currently bound is deleted, the binding
2382 // for that object reverts to zero and the default vertex array becomes current.
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002383 if (mGLState.removeVertexArrayBinding(vertexArray))
Jamie Madill57a89722013-07-02 11:57:03 -04002384 {
2385 bindVertexArray(0);
2386 }
2387}
2388
Geoff Langc8058452014-02-03 12:04:11 -05002389void Context::detachTransformFeedback(GLuint transformFeedback)
2390{
Corentin Walleza2257da2016-04-19 16:43:12 -04002391 // Transform feedback detachment is handled by Context, because 0 is a valid
2392 // transform feedback, and a pointer to it must be passed from Context to State at
2393 // binding time.
2394
2395 // The OpenGL specification doesn't mention what should happen when the currently bound
2396 // transform feedback object is deleted. Since it is a container object, we treat it like
2397 // VAOs and FBOs and set the current bound transform feedback back to 0.
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002398 if (mGLState.removeTransformFeedbackBinding(transformFeedback))
Corentin Walleza2257da2016-04-19 16:43:12 -04002399 {
2400 bindTransformFeedback(0);
2401 }
Geoff Langc8058452014-02-03 12:04:11 -05002402}
2403
Jamie Madilldc356042013-07-19 16:36:57 -04002404void Context::detachSampler(GLuint sampler)
2405{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002406 mGLState.detachSampler(sampler);
Jamie Madilldc356042013-07-19 16:36:57 -04002407}
2408
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002409void Context::setVertexAttribDivisor(GLuint index, GLuint divisor)
2410{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002411 mGLState.setVertexAttribDivisor(index, divisor);
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002412}
2413
Jamie Madille29d1672013-07-19 16:36:57 -04002414void Context::samplerParameteri(GLuint sampler, GLenum pname, GLint param)
2415{
Geoff Langc1984ed2016-10-07 12:41:00 -04002416 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002417 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002418 SetSamplerParameteri(samplerObject, pname, param);
2419}
Jamie Madille29d1672013-07-19 16:36:57 -04002420
Geoff Langc1984ed2016-10-07 12:41:00 -04002421void Context::samplerParameteriv(GLuint sampler, GLenum pname, const GLint *param)
2422{
2423 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002424 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002425 SetSamplerParameteriv(samplerObject, pname, param);
Jamie Madille29d1672013-07-19 16:36:57 -04002426}
2427
2428void Context::samplerParameterf(GLuint sampler, GLenum pname, GLfloat param)
2429{
Geoff Langc1984ed2016-10-07 12:41:00 -04002430 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002431 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002432 SetSamplerParameterf(samplerObject, pname, param);
Jamie Madille29d1672013-07-19 16:36:57 -04002433}
2434
Geoff Langc1984ed2016-10-07 12:41:00 -04002435void Context::samplerParameterfv(GLuint sampler, GLenum pname, const GLfloat *param)
Jamie Madill9675b802013-07-19 16:36:59 -04002436{
Geoff Langc1984ed2016-10-07 12:41:00 -04002437 Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002438 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002439 SetSamplerParameterfv(samplerObject, pname, param);
Jamie Madill9675b802013-07-19 16:36:59 -04002440}
2441
Geoff Langc1984ed2016-10-07 12:41:00 -04002442void Context::getSamplerParameteriv(GLuint sampler, GLenum pname, GLint *params)
Jamie Madill9675b802013-07-19 16:36:59 -04002443{
Geoff Langc1984ed2016-10-07 12:41:00 -04002444 const Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002445 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002446 QuerySamplerParameteriv(samplerObject, pname, params);
2447}
Jamie Madill9675b802013-07-19 16:36:59 -04002448
Geoff Langc1984ed2016-10-07 12:41:00 -04002449void Context::getSamplerParameterfv(GLuint sampler, GLenum pname, GLfloat *params)
2450{
2451 const Sampler *samplerObject =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05002452 mState.mSamplers->checkSamplerAllocation(mImplementation.get(), sampler);
Geoff Langc1984ed2016-10-07 12:41:00 -04002453 QuerySamplerParameterfv(samplerObject, pname, params);
Jamie Madill9675b802013-07-19 16:36:59 -04002454}
2455
Olli Etuahof0fee072016-03-30 15:11:58 +03002456void Context::programParameteri(GLuint program, GLenum pname, GLint value)
2457{
2458 gl::Program *programObject = getProgram(program);
Yunchao He61afff12017-03-14 15:34:03 +08002459 SetProgramParameteri(programObject, pname, value);
Olli Etuahof0fee072016-03-30 15:11:58 +03002460}
2461
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002462void Context::initRendererString()
2463{
daniel@transgaming.comca1ac1f2013-01-11 04:13:05 +00002464 std::ostringstream rendererString;
2465 rendererString << "ANGLE (";
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002466 rendererString << mImplementation->getRendererDescription();
daniel@transgaming.comca1ac1f2013-01-11 04:13:05 +00002467 rendererString << ")";
2468
Geoff Langcec35902014-04-16 10:52:36 -04002469 mRendererString = MakeStaticString(rendererString.str());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002470}
2471
Geoff Langc339c4e2016-11-29 10:37:36 -05002472void Context::initVersionStrings()
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002473{
Geoff Langc339c4e2016-11-29 10:37:36 -05002474 const Version &clientVersion = getClientVersion();
2475
2476 std::ostringstream versionString;
2477 versionString << "OpenGL ES " << clientVersion.major << "." << clientVersion.minor << " (ANGLE "
2478 << ANGLE_VERSION_STRING << ")";
2479 mVersionString = MakeStaticString(versionString.str());
2480
2481 std::ostringstream shadingLanguageVersionString;
2482 shadingLanguageVersionString << "OpenGL ES GLSL ES "
2483 << (clientVersion.major == 2 ? 1 : clientVersion.major) << "."
2484 << clientVersion.minor << "0 (ANGLE " << ANGLE_VERSION_STRING
2485 << ")";
2486 mShadingLanguageString = MakeStaticString(shadingLanguageVersionString.str());
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002487}
2488
Geoff Langcec35902014-04-16 10:52:36 -04002489void Context::initExtensionStrings()
2490{
Geoff Langc339c4e2016-11-29 10:37:36 -05002491 auto mergeExtensionStrings = [](const std::vector<const char *> &strings) {
2492 std::ostringstream combinedStringStream;
2493 std::copy(strings.begin(), strings.end(),
2494 std::ostream_iterator<const char *>(combinedStringStream, " "));
2495 return MakeStaticString(combinedStringStream.str());
2496 };
2497
2498 mExtensionStrings.clear();
Geoff Langc287ea62016-09-16 14:46:51 -04002499 for (const auto &extensionString : mExtensions.getStrings())
2500 {
2501 mExtensionStrings.push_back(MakeStaticString(extensionString));
2502 }
Geoff Langc339c4e2016-11-29 10:37:36 -05002503 mExtensionString = mergeExtensionStrings(mExtensionStrings);
Geoff Langcec35902014-04-16 10:52:36 -04002504
Bryan Bernhart58806562017-01-05 13:09:31 -08002505 const gl::Extensions &nativeExtensions = mImplementation->getNativeExtensions();
2506
Geoff Langc339c4e2016-11-29 10:37:36 -05002507 mRequestableExtensionStrings.clear();
2508 for (const auto &extensionInfo : GetExtensionInfoMap())
2509 {
2510 if (extensionInfo.second.Requestable &&
Bryan Bernhart58806562017-01-05 13:09:31 -08002511 !(mExtensions.*(extensionInfo.second.ExtensionsMember)) &&
2512 nativeExtensions.*(extensionInfo.second.ExtensionsMember))
Geoff Langc339c4e2016-11-29 10:37:36 -05002513 {
2514 mRequestableExtensionStrings.push_back(MakeStaticString(extensionInfo.first));
2515 }
2516 }
2517 mRequestableExtensionString = mergeExtensionStrings(mRequestableExtensionStrings);
Geoff Langcec35902014-04-16 10:52:36 -04002518}
2519
Geoff Langc339c4e2016-11-29 10:37:36 -05002520const GLubyte *Context::getString(GLenum name) const
Geoff Langcec35902014-04-16 10:52:36 -04002521{
Geoff Langc339c4e2016-11-29 10:37:36 -05002522 switch (name)
2523 {
2524 case GL_VENDOR:
2525 return reinterpret_cast<const GLubyte *>("Google Inc.");
2526
2527 case GL_RENDERER:
2528 return reinterpret_cast<const GLubyte *>(mRendererString);
2529
2530 case GL_VERSION:
2531 return reinterpret_cast<const GLubyte *>(mVersionString);
2532
2533 case GL_SHADING_LANGUAGE_VERSION:
2534 return reinterpret_cast<const GLubyte *>(mShadingLanguageString);
2535
2536 case GL_EXTENSIONS:
2537 return reinterpret_cast<const GLubyte *>(mExtensionString);
2538
2539 case GL_REQUESTABLE_EXTENSIONS_ANGLE:
2540 return reinterpret_cast<const GLubyte *>(mRequestableExtensionString);
2541
2542 default:
2543 UNREACHABLE();
2544 return nullptr;
2545 }
Geoff Langcec35902014-04-16 10:52:36 -04002546}
2547
Geoff Langc339c4e2016-11-29 10:37:36 -05002548const GLubyte *Context::getStringi(GLenum name, GLuint index) const
Geoff Langcec35902014-04-16 10:52:36 -04002549{
Geoff Langc339c4e2016-11-29 10:37:36 -05002550 switch (name)
2551 {
2552 case GL_EXTENSIONS:
2553 return reinterpret_cast<const GLubyte *>(mExtensionStrings[index]);
2554
2555 case GL_REQUESTABLE_EXTENSIONS_ANGLE:
2556 return reinterpret_cast<const GLubyte *>(mRequestableExtensionStrings[index]);
2557
2558 default:
2559 UNREACHABLE();
2560 return nullptr;
2561 }
Geoff Langcec35902014-04-16 10:52:36 -04002562}
2563
2564size_t Context::getExtensionStringCount() const
2565{
2566 return mExtensionStrings.size();
2567}
2568
Geoff Langc339c4e2016-11-29 10:37:36 -05002569void Context::requestExtension(const char *name)
2570{
2571 const ExtensionInfoMap &extensionInfos = GetExtensionInfoMap();
2572 ASSERT(extensionInfos.find(name) != extensionInfos.end());
2573 const auto &extension = extensionInfos.at(name);
2574 ASSERT(extension.Requestable);
2575
2576 if (mExtensions.*(extension.ExtensionsMember))
2577 {
2578 // Extension already enabled
2579 return;
2580 }
2581
2582 mExtensions.*(extension.ExtensionsMember) = true;
2583 updateCaps();
2584 initExtensionStrings();
Bryan Bernhart58806562017-01-05 13:09:31 -08002585
Jamie Madill2f348d22017-06-05 10:50:59 -04002586 // Release the shader compiler so it will be re-created with the requested extensions enabled.
2587 releaseShaderCompiler();
Geoff Lang9aded172017-04-05 11:07:56 -04002588
2589 // Invalidate all cached completenesses for textures and framebuffer. Some extensions make new
2590 // formats renderable or sampleable.
2591 mState.mTextures->invalidateTextureComplenessCache();
2592 for (auto &zeroTexture : mZeroTextures)
2593 {
2594 zeroTexture.second->invalidateCompletenessCache();
2595 }
2596
2597 mState.mFramebuffers->invalidateFramebufferComplenessCache();
Geoff Langc339c4e2016-11-29 10:37:36 -05002598}
2599
2600size_t Context::getRequestableExtensionStringCount() const
2601{
2602 return mRequestableExtensionStrings.size();
2603}
2604
Olli Etuahoc3e55a42016-03-09 16:29:18 +02002605void Context::beginTransformFeedback(GLenum primitiveMode)
2606{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002607 TransformFeedback *transformFeedback = mGLState.getCurrentTransformFeedback();
Olli Etuahoc3e55a42016-03-09 16:29:18 +02002608 ASSERT(transformFeedback != nullptr);
2609 ASSERT(!transformFeedback->isPaused());
2610
Jamie Madill6c1f6712017-02-14 19:08:04 -05002611 transformFeedback->begin(this, primitiveMode, mGLState.getProgram());
Olli Etuahoc3e55a42016-03-09 16:29:18 +02002612}
2613
2614bool Context::hasActiveTransformFeedback(GLuint program) const
2615{
2616 for (auto pair : mTransformFeedbackMap)
2617 {
2618 if (pair.second != nullptr && pair.second->hasBoundProgram(program))
2619 {
2620 return true;
2621 }
2622 }
2623 return false;
2624}
2625
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002626void Context::initCaps(const egl::DisplayExtensions &displayExtensions)
Geoff Lang493daf52014-07-03 13:38:44 -04002627{
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002628 mCaps = mImplementation->getNativeCaps();
Geoff Lang493daf52014-07-03 13:38:44 -04002629
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002630 mExtensions = mImplementation->getNativeExtensions();
Geoff Lang493daf52014-07-03 13:38:44 -04002631
Jamie Madill53ea9cc2016-05-17 10:12:52 -04002632 mLimitations = mImplementation->getNativeLimitations();
Austin Kinross02df7962015-07-01 10:03:42 -07002633
Geoff Langeb66a6e2016-10-31 13:06:12 -04002634 if (getClientVersion() < Version(3, 0))
Geoff Lang493daf52014-07-03 13:38:44 -04002635 {
2636 // Disable ES3+ extensions
Jamie Madill231c7f52017-04-26 13:45:37 -04002637 mExtensions.colorBufferFloat = false;
Geoff Langb66a9092016-05-16 15:59:14 -04002638 mExtensions.eglImageExternalEssl3 = false;
Vincent Lang25ab4512016-05-13 18:13:59 +02002639 mExtensions.textureNorm16 = false;
Geoff Lang493daf52014-07-03 13:38:44 -04002640 }
2641
Geoff Langeb66a6e2016-10-31 13:06:12 -04002642 if (getClientVersion() > Version(2, 0))
Geoff Lang493daf52014-07-03 13:38:44 -04002643 {
2644 // FIXME(geofflang): Don't support EXT_sRGB in non-ES2 contexts
Jamie Madill231c7f52017-04-26 13:45:37 -04002645 // mExtensions.sRGB = false;
Geoff Lang493daf52014-07-03 13:38:44 -04002646 }
2647
Jamie Madill00ed7a12016-05-19 13:13:38 -04002648 // Some extensions are always available because they are implemented in the GL layer.
Jamie Madill231c7f52017-04-26 13:45:37 -04002649 mExtensions.bindUniformLocation = true;
2650 mExtensions.vertexArrayObject = true;
Geoff Langf41a7152016-09-19 15:11:17 -04002651 mExtensions.bindGeneratesResource = true;
Geoff Langfeb8c682017-02-13 16:07:35 -05002652 mExtensions.clientArrays = true;
Geoff Langc339c4e2016-11-29 10:37:36 -05002653 mExtensions.requestExtension = true;
Jamie Madill00ed7a12016-05-19 13:13:38 -04002654
2655 // Enable the no error extension if the context was created with the flag.
2656 mExtensions.noError = mSkipValidation;
2657
Corentin Wallezccab69d2017-01-27 16:57:15 -05002658 // Enable surfaceless to advertise we'll have the correct behavior when there is no default FBO
Corentin Wallezc295e512017-01-27 17:47:50 -05002659 mExtensions.surfacelessContext = displayExtensions.surfacelessContext;
Corentin Wallezccab69d2017-01-27 16:57:15 -05002660
Geoff Lang70d0f492015-12-10 17:45:46 -05002661 // Explicitly enable GL_KHR_debug
2662 mExtensions.debug = true;
2663 mExtensions.maxDebugMessageLength = 1024;
2664 mExtensions.maxDebugLoggedMessages = 1024;
2665 mExtensions.maxDebugGroupStackDepth = 1024;
2666 mExtensions.maxLabelLength = 1024;
2667
Geoff Langff5b2d52016-09-07 11:32:23 -04002668 // Explicitly enable GL_ANGLE_robust_client_memory
2669 mExtensions.robustClientMemory = true;
2670
Jamie Madille08a1d32017-03-07 17:24:06 -05002671 // Determine robust resource init availability from EGL.
2672 mExtensions.robustResourceInitialization =
Jamie Madill948bbe52017-06-01 13:10:42 -04002673 egl::Display::GetClientExtensions().displayRobustResourceInitialization;
Jamie Madille08a1d32017-03-07 17:24:06 -05002674
Geoff Lang301d1612014-07-09 10:34:37 -04002675 // Apply implementation limits
2676 mCaps.maxVertexAttributes = std::min<GLuint>(mCaps.maxVertexAttributes, MAX_VERTEX_ATTRIBS);
Jiawei-Shao2597fb62016-12-09 16:38:02 +08002677 mCaps.maxVertexAttribBindings =
2678 getClientVersion() < ES_3_1
2679 ? mCaps.maxVertexAttributes
2680 : std::min<GLuint>(mCaps.maxVertexAttribBindings, MAX_VERTEX_ATTRIB_BINDINGS);
2681
Jamie Madill231c7f52017-04-26 13:45:37 -04002682 mCaps.maxVertexUniformBlocks = std::min<GLuint>(
2683 mCaps.maxVertexUniformBlocks, IMPLEMENTATION_MAX_VERTEX_SHADER_UNIFORM_BUFFERS);
2684 mCaps.maxVertexOutputComponents =
2685 std::min<GLuint>(mCaps.maxVertexOutputComponents, IMPLEMENTATION_MAX_VARYING_VECTORS * 4);
Geoff Lang301d1612014-07-09 10:34:37 -04002686
Jamie Madill231c7f52017-04-26 13:45:37 -04002687 mCaps.maxFragmentInputComponents =
2688 std::min<GLuint>(mCaps.maxFragmentInputComponents, IMPLEMENTATION_MAX_VARYING_VECTORS * 4);
Geoff Lang3a61c322014-07-10 13:01:54 -04002689
Geoff Langc287ea62016-09-16 14:46:51 -04002690 // WebGL compatibility
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002691 mExtensions.webglCompatibility = mWebGLContext;
Geoff Langc287ea62016-09-16 14:46:51 -04002692 for (const auto &extensionInfo : GetExtensionInfoMap())
2693 {
2694 // If this context is for WebGL, disable all enableable extensions
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002695 if (mWebGLContext && extensionInfo.second.Requestable)
Geoff Langc287ea62016-09-16 14:46:51 -04002696 {
2697 mExtensions.*(extensionInfo.second.ExtensionsMember) = false;
2698 }
2699 }
2700
2701 // Generate texture caps
2702 updateCaps();
2703}
2704
2705void Context::updateCaps()
2706{
Geoff Lang900013c2014-07-07 11:32:19 -04002707 mCaps.compressedTextureFormats.clear();
Geoff Langc287ea62016-09-16 14:46:51 -04002708 mTextureCaps.clear();
Geoff Lang900013c2014-07-07 11:32:19 -04002709
Jamie Madill4e0e6f82017-02-17 11:06:03 -05002710 for (auto capsIt : mImplementation->getNativeTextureCaps())
Geoff Lang493daf52014-07-03 13:38:44 -04002711 {
Geoff Langca271392017-04-05 12:30:00 -04002712 GLenum sizedInternalFormat = capsIt.first;
Jamie Madill231c7f52017-04-26 13:45:37 -04002713 TextureCaps formatCaps = capsIt.second;
Geoff Lang493daf52014-07-03 13:38:44 -04002714
Geoff Langca271392017-04-05 12:30:00 -04002715 const InternalFormat &formatInfo = GetSizedInternalFormatInfo(sizedInternalFormat);
Geoff Langd87878e2014-09-19 15:42:59 -04002716
Geoff Lang0d8b7242015-09-09 14:56:53 -04002717 // Update the format caps based on the client version and extensions.
2718 // Caps are AND'd with the renderer caps because some core formats are still unsupported in
2719 // ES3.
2720 formatCaps.texturable =
Geoff Langeb66a6e2016-10-31 13:06:12 -04002721 formatCaps.texturable && formatInfo.textureSupport(getClientVersion(), mExtensions);
Geoff Lang0d8b7242015-09-09 14:56:53 -04002722 formatCaps.renderable =
Geoff Langeb66a6e2016-10-31 13:06:12 -04002723 formatCaps.renderable && formatInfo.renderSupport(getClientVersion(), mExtensions);
Geoff Lang0d8b7242015-09-09 14:56:53 -04002724 formatCaps.filterable =
Geoff Langeb66a6e2016-10-31 13:06:12 -04002725 formatCaps.filterable && formatInfo.filterSupport(getClientVersion(), mExtensions);
Geoff Langd87878e2014-09-19 15:42:59 -04002726
He Yunchaoccd8c9b2017-01-18 17:36:14 +08002727 // OpenGL ES does not support multisampling with non-rendererable formats
2728 // OpenGL ES 3.0 or prior does not support multisampling with integer formats
2729 if (!formatInfo.renderSupport ||
2730 (getClientVersion() < ES_3_1 &&
2731 (formatInfo.componentType == GL_INT || formatInfo.componentType == GL_UNSIGNED_INT)))
Geoff Lang493daf52014-07-03 13:38:44 -04002732 {
Geoff Langd87878e2014-09-19 15:42:59 -04002733 formatCaps.sampleCounts.clear();
Geoff Lang493daf52014-07-03 13:38:44 -04002734 }
Geoff Langd87878e2014-09-19 15:42:59 -04002735
2736 if (formatCaps.texturable && formatInfo.compressed)
2737 {
Geoff Langca271392017-04-05 12:30:00 -04002738 mCaps.compressedTextureFormats.push_back(sizedInternalFormat);
Geoff Langd87878e2014-09-19 15:42:59 -04002739 }
2740
Geoff Langca271392017-04-05 12:30:00 -04002741 mTextureCaps.insert(sizedInternalFormat, formatCaps);
Geoff Lang493daf52014-07-03 13:38:44 -04002742 }
2743}
2744
Kenneth Russellf2f6f652016-10-05 19:53:23 -07002745void Context::initWorkarounds()
2746{
2747 // Lose the context upon out of memory error if the application is
2748 // expecting to watch for those events.
2749 mWorkarounds.loseContextOnOutOfMemory = (mResetStrategy == GL_LOSE_CONTEXT_ON_RESET_EXT);
2750}
2751
Jamie Madill1b94d432015-08-07 13:23:23 -04002752void Context::syncRendererState()
2753{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002754 const State::DirtyBits &dirtyBits = mGLState.getDirtyBits();
Frank Henigman5a53d542017-02-16 21:24:10 -05002755 mImplementation->syncState(dirtyBits);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002756 mGLState.clearDirtyBits();
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002757 mGLState.syncDirtyObjects(this);
Jamie Madill1b94d432015-08-07 13:23:23 -04002758}
2759
Jamie Madillad9f24e2016-02-12 09:27:24 -05002760void Context::syncRendererState(const State::DirtyBits &bitMask,
2761 const State::DirtyObjects &objectMask)
Jamie Madill1b94d432015-08-07 13:23:23 -04002762{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002763 const State::DirtyBits &dirtyBits = (mGLState.getDirtyBits() & bitMask);
Frank Henigman5a53d542017-02-16 21:24:10 -05002764 mImplementation->syncState(dirtyBits);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002765 mGLState.clearDirtyBits(dirtyBits);
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002766 mGLState.syncDirtyObjects(this, objectMask);
Jamie Madill1b94d432015-08-07 13:23:23 -04002767}
Jamie Madillc29968b2016-01-20 11:17:23 -05002768
2769void Context::blitFramebuffer(GLint srcX0,
2770 GLint srcY0,
2771 GLint srcX1,
2772 GLint srcY1,
2773 GLint dstX0,
2774 GLint dstY0,
2775 GLint dstX1,
2776 GLint dstY1,
2777 GLbitfield mask,
2778 GLenum filter)
2779{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002780 Framebuffer *drawFramebuffer = mGLState.getDrawFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002781 ASSERT(drawFramebuffer);
2782
2783 Rectangle srcArea(srcX0, srcY0, srcX1 - srcX0, srcY1 - srcY0);
2784 Rectangle dstArea(dstX0, dstY0, dstX1 - dstX0, dstY1 - dstY0);
2785
Jamie Madillad9f24e2016-02-12 09:27:24 -05002786 syncStateForBlit();
Jamie Madillc29968b2016-01-20 11:17:23 -05002787
Jamie Madillc564c072017-06-01 12:45:42 -04002788 handleError(drawFramebuffer->blit(this, srcArea, dstArea, mask, filter));
apatrick@chromium.org144f2802012-07-12 01:42:34 +00002789}
Jamie Madillc29968b2016-01-20 11:17:23 -05002790
2791void Context::clear(GLbitfield mask)
2792{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002793 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002794 handleError(mGLState.getDrawFramebuffer()->clear(this, mask));
Jamie Madillc29968b2016-01-20 11:17:23 -05002795}
2796
2797void Context::clearBufferfv(GLenum buffer, GLint drawbuffer, const GLfloat *values)
2798{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002799 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002800 handleError(mGLState.getDrawFramebuffer()->clearBufferfv(this, buffer, drawbuffer, values));
Jamie Madillc29968b2016-01-20 11:17:23 -05002801}
2802
2803void Context::clearBufferuiv(GLenum buffer, GLint drawbuffer, const GLuint *values)
2804{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002805 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002806 handleError(mGLState.getDrawFramebuffer()->clearBufferuiv(this, buffer, drawbuffer, values));
Jamie Madillc29968b2016-01-20 11:17:23 -05002807}
2808
2809void Context::clearBufferiv(GLenum buffer, GLint drawbuffer, const GLint *values)
2810{
Jamie Madillad9f24e2016-02-12 09:27:24 -05002811 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002812 handleError(mGLState.getDrawFramebuffer()->clearBufferiv(this, buffer, drawbuffer, values));
Jamie Madillc29968b2016-01-20 11:17:23 -05002813}
2814
2815void Context::clearBufferfi(GLenum buffer, GLint drawbuffer, GLfloat depth, GLint stencil)
2816{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002817 Framebuffer *framebufferObject = mGLState.getDrawFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002818 ASSERT(framebufferObject);
2819
2820 // If a buffer is not present, the clear has no effect
2821 if (framebufferObject->getDepthbuffer() == nullptr &&
2822 framebufferObject->getStencilbuffer() == nullptr)
2823 {
2824 return;
2825 }
2826
Jamie Madillad9f24e2016-02-12 09:27:24 -05002827 syncStateForClear();
Jamie Madillc564c072017-06-01 12:45:42 -04002828 handleError(framebufferObject->clearBufferfi(this, buffer, drawbuffer, depth, stencil));
Jamie Madillc29968b2016-01-20 11:17:23 -05002829}
2830
2831void Context::readPixels(GLint x,
2832 GLint y,
2833 GLsizei width,
2834 GLsizei height,
2835 GLenum format,
2836 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04002837 void *pixels)
Jamie Madillc29968b2016-01-20 11:17:23 -05002838{
Corentin Wallez9a8d3662016-09-22 12:18:29 -04002839 if (width == 0 || height == 0)
2840 {
2841 return;
2842 }
2843
Jamie Madillad9f24e2016-02-12 09:27:24 -05002844 syncStateForReadPixels();
Jamie Madillc29968b2016-01-20 11:17:23 -05002845
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002846 Framebuffer *framebufferObject = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002847 ASSERT(framebufferObject);
2848
2849 Rectangle area(x, y, width, height);
Jamie Madillc564c072017-06-01 12:45:42 -04002850 handleError(framebufferObject->readPixels(this, area, format, type, pixels));
Jamie Madillc29968b2016-01-20 11:17:23 -05002851}
2852
2853void Context::copyTexImage2D(GLenum target,
2854 GLint level,
2855 GLenum internalformat,
2856 GLint x,
2857 GLint y,
2858 GLsizei width,
2859 GLsizei height,
2860 GLint border)
2861{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002862 // Only sync the read FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002863 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002864
Jamie Madillc29968b2016-01-20 11:17:23 -05002865 Rectangle sourceArea(x, y, width, height);
2866
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002867 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002868 Texture *texture =
2869 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05002870 handleError(texture->copyImage(this, target, level, sourceArea, internalformat, framebuffer));
Jamie Madillc29968b2016-01-20 11:17:23 -05002871}
2872
2873void Context::copyTexSubImage2D(GLenum target,
2874 GLint level,
2875 GLint xoffset,
2876 GLint yoffset,
2877 GLint x,
2878 GLint y,
2879 GLsizei width,
2880 GLsizei height)
2881{
Corentin Wallez9a8d3662016-09-22 12:18:29 -04002882 if (width == 0 || height == 0)
2883 {
2884 return;
2885 }
2886
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002887 // Only sync the read FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002888 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002889
Jamie Madillc29968b2016-01-20 11:17:23 -05002890 Offset destOffset(xoffset, yoffset, 0);
2891 Rectangle sourceArea(x, y, width, height);
2892
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002893 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002894 Texture *texture =
2895 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05002896 handleError(texture->copySubImage(this, target, level, destOffset, sourceArea, framebuffer));
Jamie Madillc29968b2016-01-20 11:17:23 -05002897}
2898
2899void Context::copyTexSubImage3D(GLenum target,
2900 GLint level,
2901 GLint xoffset,
2902 GLint yoffset,
2903 GLint zoffset,
2904 GLint x,
2905 GLint y,
2906 GLsizei width,
2907 GLsizei height)
2908{
Corentin Wallez9a8d3662016-09-22 12:18:29 -04002909 if (width == 0 || height == 0)
2910 {
2911 return;
2912 }
2913
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002914 // Only sync the read FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04002915 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002916
Jamie Madillc29968b2016-01-20 11:17:23 -05002917 Offset destOffset(xoffset, yoffset, zoffset);
2918 Rectangle sourceArea(x, y, width, height);
2919
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002920 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05002921 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05002922 handleError(texture->copySubImage(this, target, level, destOffset, sourceArea, framebuffer));
Jamie Madillc29968b2016-01-20 11:17:23 -05002923}
2924
2925void Context::framebufferTexture2D(GLenum target,
2926 GLenum attachment,
2927 GLenum textarget,
2928 GLuint texture,
2929 GLint level)
2930{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002931 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05002932 ASSERT(framebuffer);
2933
2934 if (texture != 0)
2935 {
2936 Texture *textureObj = getTexture(texture);
2937
2938 ImageIndex index = ImageIndex::MakeInvalid();
2939
2940 if (textarget == GL_TEXTURE_2D)
2941 {
2942 index = ImageIndex::Make2D(level);
2943 }
JiangYizhoubddc46b2016-12-09 09:50:51 +08002944 else if (textarget == GL_TEXTURE_2D_MULTISAMPLE)
2945 {
2946 ASSERT(level == 0);
2947 index = ImageIndex::Make2DMultisample();
2948 }
Jamie Madillc29968b2016-01-20 11:17:23 -05002949 else
2950 {
2951 ASSERT(IsCubeMapTextureTarget(textarget));
2952 index = ImageIndex::MakeCube(textarget, level);
2953 }
2954
Jamie Madilla02315b2017-02-23 14:14:47 -05002955 framebuffer->setAttachment(this, GL_TEXTURE, attachment, index, textureObj);
Jamie Madillc29968b2016-01-20 11:17:23 -05002956 }
2957 else
2958 {
Jamie Madilla02315b2017-02-23 14:14:47 -05002959 framebuffer->resetAttachment(this, attachment);
Jamie Madillc29968b2016-01-20 11:17:23 -05002960 }
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002961
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002962 mGLState.setObjectDirty(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05002963}
2964
2965void Context::framebufferRenderbuffer(GLenum target,
2966 GLenum attachment,
2967 GLenum renderbuffertarget,
2968 GLuint renderbuffer)
2969{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002970 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05002971 ASSERT(framebuffer);
2972
2973 if (renderbuffer != 0)
2974 {
2975 Renderbuffer *renderbufferObject = getRenderbuffer(renderbuffer);
Jamie Madilla02315b2017-02-23 14:14:47 -05002976
2977 framebuffer->setAttachment(this, GL_RENDERBUFFER, attachment, gl::ImageIndex::MakeInvalid(),
Jamie Madillc29968b2016-01-20 11:17:23 -05002978 renderbufferObject);
2979 }
2980 else
2981 {
Jamie Madilla02315b2017-02-23 14:14:47 -05002982 framebuffer->resetAttachment(this, attachment);
Jamie Madillc29968b2016-01-20 11:17:23 -05002983 }
Jamie Madill60ec6ea2016-01-22 15:27:19 -05002984
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002985 mGLState.setObjectDirty(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05002986}
2987
2988void Context::framebufferTextureLayer(GLenum target,
2989 GLenum attachment,
2990 GLuint texture,
2991 GLint level,
2992 GLint layer)
2993{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07002994 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05002995 ASSERT(framebuffer);
2996
2997 if (texture != 0)
2998 {
2999 Texture *textureObject = getTexture(texture);
3000
3001 ImageIndex index = ImageIndex::MakeInvalid();
3002
3003 if (textureObject->getTarget() == GL_TEXTURE_3D)
3004 {
3005 index = ImageIndex::Make3D(level, layer);
3006 }
3007 else
3008 {
3009 ASSERT(textureObject->getTarget() == GL_TEXTURE_2D_ARRAY);
3010 index = ImageIndex::Make2DArray(level, layer);
3011 }
3012
Jamie Madilla02315b2017-02-23 14:14:47 -05003013 framebuffer->setAttachment(this, GL_TEXTURE, attachment, index, textureObject);
Jamie Madillc29968b2016-01-20 11:17:23 -05003014 }
3015 else
3016 {
Jamie Madilla02315b2017-02-23 14:14:47 -05003017 framebuffer->resetAttachment(this, attachment);
Jamie Madillc29968b2016-01-20 11:17:23 -05003018 }
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003019
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003020 mGLState.setObjectDirty(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003021}
3022
3023void Context::drawBuffers(GLsizei n, const GLenum *bufs)
3024{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003025 Framebuffer *framebuffer = mGLState.getDrawFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05003026 ASSERT(framebuffer);
3027 framebuffer->setDrawBuffers(n, bufs);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003028 mGLState.setObjectDirty(GL_DRAW_FRAMEBUFFER);
Jamie Madillc29968b2016-01-20 11:17:23 -05003029}
3030
3031void Context::readBuffer(GLenum mode)
3032{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003033 Framebuffer *readFBO = mGLState.getReadFramebuffer();
Jamie Madillc29968b2016-01-20 11:17:23 -05003034 readFBO->setReadBuffer(mode);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003035 mGLState.setObjectDirty(GL_READ_FRAMEBUFFER);
Jamie Madillc29968b2016-01-20 11:17:23 -05003036}
3037
3038void Context::discardFramebuffer(GLenum target, GLsizei numAttachments, const GLenum *attachments)
3039{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003040 // Only sync the FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003041 mGLState.syncDirtyObject(this, target);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003042
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003043 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003044 ASSERT(framebuffer);
3045
3046 // The specification isn't clear what should be done when the framebuffer isn't complete.
3047 // We leave it up to the framebuffer implementation to decide what to do.
Jamie Madill437fa652016-05-03 15:13:24 -04003048 handleError(framebuffer->discard(numAttachments, attachments));
Jamie Madillc29968b2016-01-20 11:17:23 -05003049}
3050
3051void Context::invalidateFramebuffer(GLenum target,
3052 GLsizei numAttachments,
3053 const GLenum *attachments)
3054{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003055 // Only sync the FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003056 mGLState.syncDirtyObject(this, target);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003057
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003058 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003059 ASSERT(framebuffer);
3060
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003061 if (framebuffer->checkStatus(this) != GL_FRAMEBUFFER_COMPLETE)
Jamie Madillc29968b2016-01-20 11:17:23 -05003062 {
Jamie Madill437fa652016-05-03 15:13:24 -04003063 return;
Jamie Madillc29968b2016-01-20 11:17:23 -05003064 }
Jamie Madill437fa652016-05-03 15:13:24 -04003065
3066 handleError(framebuffer->invalidate(numAttachments, attachments));
Jamie Madillc29968b2016-01-20 11:17:23 -05003067}
3068
3069void Context::invalidateSubFramebuffer(GLenum target,
3070 GLsizei numAttachments,
3071 const GLenum *attachments,
3072 GLint x,
3073 GLint y,
3074 GLsizei width,
3075 GLsizei height)
3076{
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003077 // Only sync the FBO
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003078 mGLState.syncDirtyObject(this, target);
Jamie Madill60ec6ea2016-01-22 15:27:19 -05003079
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003080 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
Jamie Madillc29968b2016-01-20 11:17:23 -05003081 ASSERT(framebuffer);
3082
Jamie Madilldd43e6c2017-03-24 14:18:49 -04003083 if (framebuffer->checkStatus(this) != GL_FRAMEBUFFER_COMPLETE)
Jamie Madillc29968b2016-01-20 11:17:23 -05003084 {
Jamie Madill437fa652016-05-03 15:13:24 -04003085 return;
Jamie Madillc29968b2016-01-20 11:17:23 -05003086 }
Jamie Madill437fa652016-05-03 15:13:24 -04003087
3088 Rectangle area(x, y, width, height);
3089 handleError(framebuffer->invalidateSub(numAttachments, attachments, area));
Jamie Madillc29968b2016-01-20 11:17:23 -05003090}
3091
Jamie Madill73a84962016-02-12 09:27:23 -05003092void Context::texImage2D(GLenum target,
3093 GLint level,
3094 GLint internalformat,
3095 GLsizei width,
3096 GLsizei height,
3097 GLint border,
3098 GLenum format,
3099 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003100 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003101{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003102 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003103
3104 Extents size(width, height, 1);
3105 Texture *texture =
3106 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003107 handleError(texture->setImage(this, mGLState.getUnpackState(), target, level, internalformat,
3108 size, format, type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003109}
3110
3111void Context::texImage3D(GLenum target,
3112 GLint level,
3113 GLint internalformat,
3114 GLsizei width,
3115 GLsizei height,
3116 GLsizei depth,
3117 GLint border,
3118 GLenum format,
3119 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003120 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003121{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003122 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003123
3124 Extents size(width, height, depth);
3125 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003126 handleError(texture->setImage(this, mGLState.getUnpackState(), target, level, internalformat,
3127 size, format, type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003128}
3129
3130void Context::texSubImage2D(GLenum target,
3131 GLint level,
3132 GLint xoffset,
3133 GLint yoffset,
3134 GLsizei width,
3135 GLsizei height,
3136 GLenum format,
3137 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003138 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003139{
3140 // Zero sized uploads are valid but no-ops
3141 if (width == 0 || height == 0)
3142 {
3143 return;
3144 }
3145
Jamie Madillad9f24e2016-02-12 09:27:24 -05003146 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003147
3148 Box area(xoffset, yoffset, 0, width, height, 1);
3149 Texture *texture =
3150 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003151 handleError(texture->setSubImage(this, mGLState.getUnpackState(), target, level, area, format,
3152 type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003153}
3154
3155void Context::texSubImage3D(GLenum target,
3156 GLint level,
3157 GLint xoffset,
3158 GLint yoffset,
3159 GLint zoffset,
3160 GLsizei width,
3161 GLsizei height,
3162 GLsizei depth,
3163 GLenum format,
3164 GLenum type,
Jamie Madill876429b2017-04-20 15:46:24 -04003165 const void *pixels)
Jamie Madill73a84962016-02-12 09:27:23 -05003166{
3167 // Zero sized uploads are valid but no-ops
3168 if (width == 0 || height == 0 || depth == 0)
3169 {
3170 return;
3171 }
3172
Jamie Madillad9f24e2016-02-12 09:27:24 -05003173 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003174
3175 Box area(xoffset, yoffset, zoffset, width, height, depth);
3176 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003177 handleError(texture->setSubImage(this, mGLState.getUnpackState(), target, level, area, format,
3178 type, reinterpret_cast<const uint8_t *>(pixels)));
Jamie Madill73a84962016-02-12 09:27:23 -05003179}
3180
3181void Context::compressedTexImage2D(GLenum target,
3182 GLint level,
3183 GLenum internalformat,
3184 GLsizei width,
3185 GLsizei height,
3186 GLint border,
3187 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003188 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003189{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003190 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003191
3192 Extents size(width, height, 1);
3193 Texture *texture =
3194 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003195 handleError(texture->setCompressedImage(this, mGLState.getUnpackState(), target, level,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003196 internalformat, size, imageSize,
Jamie Madill437fa652016-05-03 15:13:24 -04003197 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003198}
3199
3200void Context::compressedTexImage3D(GLenum target,
3201 GLint level,
3202 GLenum internalformat,
3203 GLsizei width,
3204 GLsizei height,
3205 GLsizei depth,
3206 GLint border,
3207 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003208 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003209{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003210 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003211
3212 Extents size(width, height, depth);
3213 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003214 handleError(texture->setCompressedImage(this, mGLState.getUnpackState(), target, level,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003215 internalformat, size, imageSize,
Jamie Madill437fa652016-05-03 15:13:24 -04003216 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003217}
3218
3219void Context::compressedTexSubImage2D(GLenum target,
3220 GLint level,
3221 GLint xoffset,
3222 GLint yoffset,
3223 GLsizei width,
3224 GLsizei height,
3225 GLenum format,
3226 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003227 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003228{
Jamie Madillad9f24e2016-02-12 09:27:24 -05003229 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003230
3231 Box area(xoffset, yoffset, 0, width, height, 1);
3232 Texture *texture =
3233 getTargetTexture(IsCubeMapTextureTarget(target) ? GL_TEXTURE_CUBE_MAP : target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003234 handleError(texture->setCompressedSubImage(this, mGLState.getUnpackState(), target, level, area,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003235 format, imageSize,
3236 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003237}
3238
3239void Context::compressedTexSubImage3D(GLenum target,
3240 GLint level,
3241 GLint xoffset,
3242 GLint yoffset,
3243 GLint zoffset,
3244 GLsizei width,
3245 GLsizei height,
3246 GLsizei depth,
3247 GLenum format,
3248 GLsizei imageSize,
Jamie Madill876429b2017-04-20 15:46:24 -04003249 const void *data)
Jamie Madill73a84962016-02-12 09:27:23 -05003250{
3251 // Zero sized uploads are valid but no-ops
3252 if (width == 0 || height == 0)
3253 {
3254 return;
3255 }
3256
Jamie Madillad9f24e2016-02-12 09:27:24 -05003257 syncStateForTexImage();
Jamie Madill73a84962016-02-12 09:27:23 -05003258
3259 Box area(xoffset, yoffset, zoffset, width, height, depth);
3260 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003261 handleError(texture->setCompressedSubImage(this, mGLState.getUnpackState(), target, level, area,
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003262 format, imageSize,
3263 reinterpret_cast<const uint8_t *>(data)));
Jamie Madill73a84962016-02-12 09:27:23 -05003264}
3265
Olli Etuaho0f2b1562016-05-13 16:15:35 +03003266void Context::generateMipmap(GLenum target)
3267{
3268 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05003269 handleError(texture->generateMipmap(this));
Olli Etuaho0f2b1562016-05-13 16:15:35 +03003270}
3271
Geoff Lang97073d12016-04-20 10:42:34 -07003272void Context::copyTextureCHROMIUM(GLuint sourceId,
Geoff Langfc72a072017-03-24 14:52:39 -04003273 GLint sourceLevel,
3274 GLenum destTarget,
Geoff Lang97073d12016-04-20 10:42:34 -07003275 GLuint destId,
Geoff Langfc72a072017-03-24 14:52:39 -04003276 GLint destLevel,
Geoff Lang97073d12016-04-20 10:42:34 -07003277 GLint internalFormat,
3278 GLenum destType,
3279 GLboolean unpackFlipY,
3280 GLboolean unpackPremultiplyAlpha,
3281 GLboolean unpackUnmultiplyAlpha)
3282{
3283 syncStateForTexImage();
3284
3285 gl::Texture *sourceTexture = getTexture(sourceId);
3286 gl::Texture *destTexture = getTexture(destId);
Geoff Langfc72a072017-03-24 14:52:39 -04003287 handleError(destTexture->copyTexture(
3288 this, destTarget, destLevel, internalFormat, destType, sourceLevel, unpackFlipY == GL_TRUE,
3289 unpackPremultiplyAlpha == GL_TRUE, unpackUnmultiplyAlpha == GL_TRUE, sourceTexture));
Geoff Lang97073d12016-04-20 10:42:34 -07003290}
3291
3292void Context::copySubTextureCHROMIUM(GLuint sourceId,
Geoff Langfc72a072017-03-24 14:52:39 -04003293 GLint sourceLevel,
3294 GLenum destTarget,
Geoff Lang97073d12016-04-20 10:42:34 -07003295 GLuint destId,
Geoff Langfc72a072017-03-24 14:52:39 -04003296 GLint destLevel,
Geoff Lang97073d12016-04-20 10:42:34 -07003297 GLint xoffset,
3298 GLint yoffset,
3299 GLint x,
3300 GLint y,
3301 GLsizei width,
3302 GLsizei height,
3303 GLboolean unpackFlipY,
3304 GLboolean unpackPremultiplyAlpha,
3305 GLboolean unpackUnmultiplyAlpha)
3306{
3307 // Zero sized copies are valid but no-ops
3308 if (width == 0 || height == 0)
3309 {
3310 return;
3311 }
3312
3313 syncStateForTexImage();
3314
3315 gl::Texture *sourceTexture = getTexture(sourceId);
3316 gl::Texture *destTexture = getTexture(destId);
3317 Offset offset(xoffset, yoffset, 0);
3318 Rectangle area(x, y, width, height);
Geoff Langfc72a072017-03-24 14:52:39 -04003319 handleError(destTexture->copySubTexture(
3320 this, destTarget, destLevel, offset, sourceLevel, area, unpackFlipY == GL_TRUE,
3321 unpackPremultiplyAlpha == GL_TRUE, unpackUnmultiplyAlpha == GL_TRUE, sourceTexture));
Geoff Lang97073d12016-04-20 10:42:34 -07003322}
3323
Geoff Lang47110bf2016-04-20 11:13:22 -07003324void Context::compressedCopyTextureCHROMIUM(GLuint sourceId, GLuint destId)
3325{
3326 syncStateForTexImage();
3327
3328 gl::Texture *sourceTexture = getTexture(sourceId);
3329 gl::Texture *destTexture = getTexture(destId);
Jamie Madill8897afa2017-02-06 17:17:23 -05003330 handleError(destTexture->copyCompressedTexture(this, sourceTexture));
Geoff Lang47110bf2016-04-20 11:13:22 -07003331}
3332
Geoff Lang496c02d2016-10-20 11:38:11 -07003333void Context::getBufferPointerv(GLenum target, GLenum pname, void **params)
Olli Etuaho4f667482016-03-30 15:56:35 +03003334{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003335 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003336 ASSERT(buffer);
3337
Geoff Lang496c02d2016-10-20 11:38:11 -07003338 QueryBufferPointerv(buffer, pname, params);
Olli Etuaho4f667482016-03-30 15:56:35 +03003339}
3340
Jamie Madill876429b2017-04-20 15:46:24 -04003341void *Context::mapBuffer(GLenum target, GLenum access)
Olli Etuaho4f667482016-03-30 15:56:35 +03003342{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003343 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003344 ASSERT(buffer);
3345
Jamie Madill5f56ddb2017-01-13 17:29:55 -05003346 Error error = buffer->map(this, access);
Olli Etuaho4f667482016-03-30 15:56:35 +03003347 if (error.isError())
3348 {
Jamie Madill437fa652016-05-03 15:13:24 -04003349 handleError(error);
Olli Etuaho4f667482016-03-30 15:56:35 +03003350 return nullptr;
3351 }
3352
3353 return buffer->getMapPointer();
3354}
3355
3356GLboolean Context::unmapBuffer(GLenum target)
3357{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003358 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003359 ASSERT(buffer);
3360
3361 GLboolean result;
Jamie Madill5f56ddb2017-01-13 17:29:55 -05003362 Error error = buffer->unmap(this, &result);
Olli Etuaho4f667482016-03-30 15:56:35 +03003363 if (error.isError())
3364 {
Jamie Madill437fa652016-05-03 15:13:24 -04003365 handleError(error);
Olli Etuaho4f667482016-03-30 15:56:35 +03003366 return GL_FALSE;
3367 }
3368
3369 return result;
3370}
3371
Jamie Madill876429b2017-04-20 15:46:24 -04003372void *Context::mapBufferRange(GLenum target, GLintptr offset, GLsizeiptr length, GLbitfield access)
Olli Etuaho4f667482016-03-30 15:56:35 +03003373{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003374 Buffer *buffer = mGLState.getTargetBuffer(target);
Olli Etuaho4f667482016-03-30 15:56:35 +03003375 ASSERT(buffer);
3376
Jamie Madill5f56ddb2017-01-13 17:29:55 -05003377 Error error = buffer->mapRange(this, offset, length, access);
Olli Etuaho4f667482016-03-30 15:56:35 +03003378 if (error.isError())
3379 {
Jamie Madill437fa652016-05-03 15:13:24 -04003380 handleError(error);
Olli Etuaho4f667482016-03-30 15:56:35 +03003381 return nullptr;
3382 }
3383
3384 return buffer->getMapPointer();
3385}
3386
3387void Context::flushMappedBufferRange(GLenum /*target*/, GLintptr /*offset*/, GLsizeiptr /*length*/)
3388{
3389 // We do not currently support a non-trivial implementation of FlushMappedBufferRange
3390}
3391
Jamie Madillad9f24e2016-02-12 09:27:24 -05003392void Context::syncStateForReadPixels()
3393{
3394 syncRendererState(mReadPixelsDirtyBits, mReadPixelsDirtyObjects);
3395}
3396
3397void Context::syncStateForTexImage()
3398{
3399 syncRendererState(mTexImageDirtyBits, mTexImageDirtyObjects);
3400}
3401
3402void Context::syncStateForClear()
3403{
3404 syncRendererState(mClearDirtyBits, mClearDirtyObjects);
3405}
3406
3407void Context::syncStateForBlit()
3408{
3409 syncRendererState(mBlitDirtyBits, mBlitDirtyObjects);
3410}
3411
Jamie Madillc20ab272016-06-09 07:20:46 -07003412void Context::activeTexture(GLenum texture)
3413{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003414 mGLState.setActiveSampler(texture - GL_TEXTURE0);
Jamie Madillc20ab272016-06-09 07:20:46 -07003415}
3416
Jamie Madill876429b2017-04-20 15:46:24 -04003417void Context::blendColor(GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha)
Jamie Madillc20ab272016-06-09 07:20:46 -07003418{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003419 mGLState.setBlendColor(clamp01(red), clamp01(green), clamp01(blue), clamp01(alpha));
Jamie Madillc20ab272016-06-09 07:20:46 -07003420}
3421
Jamie Madill8a9e4bc2016-11-13 20:02:12 -05003422void Context::blendEquation(GLenum mode)
3423{
3424 mGLState.setBlendEquation(mode, mode);
3425}
3426
Jamie Madillc20ab272016-06-09 07:20:46 -07003427void Context::blendEquationSeparate(GLenum modeRGB, GLenum modeAlpha)
3428{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003429 mGLState.setBlendEquation(modeRGB, modeAlpha);
Jamie Madillc20ab272016-06-09 07:20:46 -07003430}
3431
Jamie Madill8a9e4bc2016-11-13 20:02:12 -05003432void Context::blendFunc(GLenum sfactor, GLenum dfactor)
3433{
3434 mGLState.setBlendFactors(sfactor, dfactor, sfactor, dfactor);
3435}
3436
Jamie Madillc20ab272016-06-09 07:20:46 -07003437void Context::blendFuncSeparate(GLenum srcRGB, GLenum dstRGB, GLenum srcAlpha, GLenum dstAlpha)
3438{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003439 mGLState.setBlendFactors(srcRGB, dstRGB, srcAlpha, dstAlpha);
Jamie Madillc20ab272016-06-09 07:20:46 -07003440}
3441
Jamie Madill876429b2017-04-20 15:46:24 -04003442void Context::clearColor(GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha)
Jamie Madillc20ab272016-06-09 07:20:46 -07003443{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003444 mGLState.setColorClearValue(red, green, blue, alpha);
Jamie Madillc20ab272016-06-09 07:20:46 -07003445}
3446
Jamie Madill876429b2017-04-20 15:46:24 -04003447void Context::clearDepthf(GLfloat depth)
Jamie Madillc20ab272016-06-09 07:20:46 -07003448{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003449 mGLState.setDepthClearValue(depth);
Jamie Madillc20ab272016-06-09 07:20:46 -07003450}
3451
3452void Context::clearStencil(GLint s)
3453{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003454 mGLState.setStencilClearValue(s);
Jamie Madillc20ab272016-06-09 07:20:46 -07003455}
3456
3457void Context::colorMask(GLboolean red, GLboolean green, GLboolean blue, GLboolean alpha)
3458{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003459 mGLState.setColorMask(red == GL_TRUE, green == GL_TRUE, blue == GL_TRUE, alpha == GL_TRUE);
Jamie Madillc20ab272016-06-09 07:20:46 -07003460}
3461
3462void Context::cullFace(GLenum mode)
3463{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003464 mGLState.setCullMode(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003465}
3466
3467void Context::depthFunc(GLenum func)
3468{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003469 mGLState.setDepthFunc(func);
Jamie Madillc20ab272016-06-09 07:20:46 -07003470}
3471
3472void Context::depthMask(GLboolean flag)
3473{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003474 mGLState.setDepthMask(flag != GL_FALSE);
Jamie Madillc20ab272016-06-09 07:20:46 -07003475}
3476
Jamie Madill876429b2017-04-20 15:46:24 -04003477void Context::depthRangef(GLfloat zNear, GLfloat zFar)
Jamie Madillc20ab272016-06-09 07:20:46 -07003478{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003479 mGLState.setDepthRange(zNear, zFar);
Jamie Madillc20ab272016-06-09 07:20:46 -07003480}
3481
3482void Context::disable(GLenum cap)
3483{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003484 mGLState.setEnableFeature(cap, false);
Jamie Madillc20ab272016-06-09 07:20:46 -07003485}
3486
3487void Context::disableVertexAttribArray(GLuint index)
3488{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003489 mGLState.setEnableVertexAttribArray(index, false);
Jamie Madillc20ab272016-06-09 07:20:46 -07003490}
3491
3492void Context::enable(GLenum cap)
3493{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003494 mGLState.setEnableFeature(cap, true);
Jamie Madillc20ab272016-06-09 07:20:46 -07003495}
3496
3497void Context::enableVertexAttribArray(GLuint index)
3498{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003499 mGLState.setEnableVertexAttribArray(index, true);
Jamie Madillc20ab272016-06-09 07:20:46 -07003500}
3501
3502void Context::frontFace(GLenum mode)
3503{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003504 mGLState.setFrontFace(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003505}
3506
3507void Context::hint(GLenum target, GLenum mode)
3508{
3509 switch (target)
3510 {
3511 case GL_GENERATE_MIPMAP_HINT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003512 mGLState.setGenerateMipmapHint(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003513 break;
3514
3515 case GL_FRAGMENT_SHADER_DERIVATIVE_HINT_OES:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003516 mGLState.setFragmentShaderDerivativeHint(mode);
Jamie Madillc20ab272016-06-09 07:20:46 -07003517 break;
3518
3519 default:
3520 UNREACHABLE();
3521 return;
3522 }
3523}
3524
3525void Context::lineWidth(GLfloat width)
3526{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003527 mGLState.setLineWidth(width);
Jamie Madillc20ab272016-06-09 07:20:46 -07003528}
3529
3530void Context::pixelStorei(GLenum pname, GLint param)
3531{
3532 switch (pname)
3533 {
3534 case GL_UNPACK_ALIGNMENT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003535 mGLState.setUnpackAlignment(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003536 break;
3537
3538 case GL_PACK_ALIGNMENT:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003539 mGLState.setPackAlignment(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003540 break;
3541
3542 case GL_PACK_REVERSE_ROW_ORDER_ANGLE:
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003543 mGLState.setPackReverseRowOrder(param != 0);
Jamie Madillc20ab272016-06-09 07:20:46 -07003544 break;
3545
3546 case GL_UNPACK_ROW_LENGTH:
Martin Radev1be913c2016-07-11 17:59:16 +03003547 ASSERT((getClientMajorVersion() >= 3) || getExtensions().unpackSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003548 mGLState.setUnpackRowLength(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003549 break;
3550
3551 case GL_UNPACK_IMAGE_HEIGHT:
Martin Radev1be913c2016-07-11 17:59:16 +03003552 ASSERT(getClientMajorVersion() >= 3);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003553 mGLState.setUnpackImageHeight(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003554 break;
3555
3556 case GL_UNPACK_SKIP_IMAGES:
Martin Radev1be913c2016-07-11 17:59:16 +03003557 ASSERT(getClientMajorVersion() >= 3);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003558 mGLState.setUnpackSkipImages(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003559 break;
3560
3561 case GL_UNPACK_SKIP_ROWS:
Martin Radev1be913c2016-07-11 17:59:16 +03003562 ASSERT((getClientMajorVersion() >= 3) || getExtensions().unpackSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003563 mGLState.setUnpackSkipRows(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003564 break;
3565
3566 case GL_UNPACK_SKIP_PIXELS:
Martin Radev1be913c2016-07-11 17:59:16 +03003567 ASSERT((getClientMajorVersion() >= 3) || getExtensions().unpackSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003568 mGLState.setUnpackSkipPixels(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003569 break;
3570
3571 case GL_PACK_ROW_LENGTH:
Martin Radev1be913c2016-07-11 17:59:16 +03003572 ASSERT((getClientMajorVersion() >= 3) || getExtensions().packSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003573 mGLState.setPackRowLength(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003574 break;
3575
3576 case GL_PACK_SKIP_ROWS:
Martin Radev1be913c2016-07-11 17:59:16 +03003577 ASSERT((getClientMajorVersion() >= 3) || getExtensions().packSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003578 mGLState.setPackSkipRows(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003579 break;
3580
3581 case GL_PACK_SKIP_PIXELS:
Martin Radev1be913c2016-07-11 17:59:16 +03003582 ASSERT((getClientMajorVersion() >= 3) || getExtensions().packSubimage);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003583 mGLState.setPackSkipPixels(param);
Jamie Madillc20ab272016-06-09 07:20:46 -07003584 break;
3585
3586 default:
3587 UNREACHABLE();
3588 return;
3589 }
3590}
3591
3592void Context::polygonOffset(GLfloat factor, GLfloat units)
3593{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003594 mGLState.setPolygonOffsetParams(factor, units);
Jamie Madillc20ab272016-06-09 07:20:46 -07003595}
3596
Jamie Madill876429b2017-04-20 15:46:24 -04003597void Context::sampleCoverage(GLfloat value, GLboolean invert)
Jamie Madillc20ab272016-06-09 07:20:46 -07003598{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003599 mGLState.setSampleCoverageParams(clamp01(value), invert == GL_TRUE);
Jamie Madillc20ab272016-06-09 07:20:46 -07003600}
3601
3602void Context::scissor(GLint x, GLint y, GLsizei width, GLsizei height)
3603{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003604 mGLState.setScissorParams(x, y, width, height);
Jamie Madillc20ab272016-06-09 07:20:46 -07003605}
3606
3607void Context::stencilFuncSeparate(GLenum face, GLenum func, GLint ref, GLuint mask)
3608{
3609 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
3610 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003611 mGLState.setStencilParams(func, ref, mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003612 }
3613
3614 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
3615 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003616 mGLState.setStencilBackParams(func, ref, mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003617 }
3618}
3619
3620void Context::stencilMaskSeparate(GLenum face, GLuint mask)
3621{
3622 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
3623 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003624 mGLState.setStencilWritemask(mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003625 }
3626
3627 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
3628 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003629 mGLState.setStencilBackWritemask(mask);
Jamie Madillc20ab272016-06-09 07:20:46 -07003630 }
3631}
3632
3633void Context::stencilOpSeparate(GLenum face, GLenum fail, GLenum zfail, GLenum zpass)
3634{
3635 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
3636 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003637 mGLState.setStencilOperations(fail, zfail, zpass);
Jamie Madillc20ab272016-06-09 07:20:46 -07003638 }
3639
3640 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
3641 {
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003642 mGLState.setStencilBackOperations(fail, zfail, zpass);
Jamie Madillc20ab272016-06-09 07:20:46 -07003643 }
3644}
3645
3646void Context::vertexAttrib1f(GLuint index, GLfloat x)
3647{
3648 GLfloat vals[4] = {x, 0, 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003649 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003650}
3651
3652void Context::vertexAttrib1fv(GLuint index, const GLfloat *values)
3653{
3654 GLfloat vals[4] = {values[0], 0, 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003655 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003656}
3657
3658void Context::vertexAttrib2f(GLuint index, GLfloat x, GLfloat y)
3659{
3660 GLfloat vals[4] = {x, y, 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003661 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003662}
3663
3664void Context::vertexAttrib2fv(GLuint index, const GLfloat *values)
3665{
3666 GLfloat vals[4] = {values[0], values[1], 0, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003667 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003668}
3669
3670void Context::vertexAttrib3f(GLuint index, GLfloat x, GLfloat y, GLfloat z)
3671{
3672 GLfloat vals[4] = {x, y, z, 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003673 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003674}
3675
3676void Context::vertexAttrib3fv(GLuint index, const GLfloat *values)
3677{
3678 GLfloat vals[4] = {values[0], values[1], values[2], 1};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003679 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003680}
3681
3682void Context::vertexAttrib4f(GLuint index, GLfloat x, GLfloat y, GLfloat z, GLfloat w)
3683{
3684 GLfloat vals[4] = {x, y, z, w};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003685 mGLState.setVertexAttribf(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003686}
3687
3688void Context::vertexAttrib4fv(GLuint index, const GLfloat *values)
3689{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003690 mGLState.setVertexAttribf(index, values);
Jamie Madillc20ab272016-06-09 07:20:46 -07003691}
3692
3693void Context::vertexAttribPointer(GLuint index,
3694 GLint size,
3695 GLenum type,
3696 GLboolean normalized,
3697 GLsizei stride,
Jamie Madill876429b2017-04-20 15:46:24 -04003698 const void *ptr)
Jamie Madillc20ab272016-06-09 07:20:46 -07003699{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003700 mGLState.setVertexAttribState(index, mGLState.getTargetBuffer(GL_ARRAY_BUFFER), size, type,
3701 normalized == GL_TRUE, false, stride, ptr);
Jamie Madillc20ab272016-06-09 07:20:46 -07003702}
3703
Shao80957d92017-02-20 21:25:59 +08003704void Context::vertexAttribFormat(GLuint attribIndex,
3705 GLint size,
3706 GLenum type,
3707 GLboolean normalized,
3708 GLuint relativeOffset)
3709{
3710 mGLState.setVertexAttribFormat(attribIndex, size, type, normalized == GL_TRUE, false,
3711 relativeOffset);
3712}
3713
3714void Context::vertexAttribIFormat(GLuint attribIndex,
3715 GLint size,
3716 GLenum type,
3717 GLuint relativeOffset)
3718{
3719 mGLState.setVertexAttribFormat(attribIndex, size, type, false, true, relativeOffset);
3720}
3721
3722void Context::vertexAttribBinding(GLuint attribIndex, GLuint bindingIndex)
3723{
3724 mGLState.setVertexAttribBinding(attribIndex, bindingIndex);
3725}
3726
3727void Context::setVertexBindingDivisor(GLuint bindingIndex, GLuint divisor)
3728{
3729 mGLState.setVertexBindingDivisor(bindingIndex, divisor);
3730}
3731
Jamie Madillc20ab272016-06-09 07:20:46 -07003732void Context::viewport(GLint x, GLint y, GLsizei width, GLsizei height)
3733{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003734 mGLState.setViewportParams(x, y, width, height);
Jamie Madillc20ab272016-06-09 07:20:46 -07003735}
3736
3737void Context::vertexAttribIPointer(GLuint index,
3738 GLint size,
3739 GLenum type,
3740 GLsizei stride,
Jamie Madill876429b2017-04-20 15:46:24 -04003741 const void *pointer)
Jamie Madillc20ab272016-06-09 07:20:46 -07003742{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003743 mGLState.setVertexAttribState(index, mGLState.getTargetBuffer(GL_ARRAY_BUFFER), size, type,
3744 false, true, stride, pointer);
Jamie Madillc20ab272016-06-09 07:20:46 -07003745}
3746
3747void Context::vertexAttribI4i(GLuint index, GLint x, GLint y, GLint z, GLint w)
3748{
3749 GLint vals[4] = {x, y, z, w};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003750 mGLState.setVertexAttribi(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003751}
3752
3753void Context::vertexAttribI4ui(GLuint index, GLuint x, GLuint y, GLuint z, GLuint w)
3754{
3755 GLuint vals[4] = {x, y, z, w};
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003756 mGLState.setVertexAttribu(index, vals);
Jamie Madillc20ab272016-06-09 07:20:46 -07003757}
3758
3759void Context::vertexAttribI4iv(GLuint index, const GLint *v)
3760{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003761 mGLState.setVertexAttribi(index, v);
Jamie Madillc20ab272016-06-09 07:20:46 -07003762}
3763
3764void Context::vertexAttribI4uiv(GLuint index, const GLuint *v)
3765{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003766 mGLState.setVertexAttribu(index, v);
Jamie Madillc20ab272016-06-09 07:20:46 -07003767}
3768
Jiawei-Shao2597fb62016-12-09 16:38:02 +08003769void Context::getVertexAttribiv(GLuint index, GLenum pname, GLint *params)
3770{
3771 const VertexAttribCurrentValueData &currentValues =
3772 getGLState().getVertexAttribCurrentValue(index);
3773 const VertexArray *vao = getGLState().getVertexArray();
3774 QueryVertexAttribiv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3775 currentValues, pname, params);
3776}
3777
3778void Context::getVertexAttribfv(GLuint index, GLenum pname, GLfloat *params)
3779{
3780 const VertexAttribCurrentValueData &currentValues =
3781 getGLState().getVertexAttribCurrentValue(index);
3782 const VertexArray *vao = getGLState().getVertexArray();
3783 QueryVertexAttribfv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3784 currentValues, pname, params);
3785}
3786
3787void Context::getVertexAttribIiv(GLuint index, GLenum pname, GLint *params)
3788{
3789 const VertexAttribCurrentValueData &currentValues =
3790 getGLState().getVertexAttribCurrentValue(index);
3791 const VertexArray *vao = getGLState().getVertexArray();
3792 QueryVertexAttribIiv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3793 currentValues, pname, params);
3794}
3795
3796void Context::getVertexAttribIuiv(GLuint index, GLenum pname, GLuint *params)
3797{
3798 const VertexAttribCurrentValueData &currentValues =
3799 getGLState().getVertexAttribCurrentValue(index);
3800 const VertexArray *vao = getGLState().getVertexArray();
3801 QueryVertexAttribIuiv(vao->getVertexAttribute(index), vao->getBindingFromAttribIndex(index),
3802 currentValues, pname, params);
3803}
3804
Jamie Madill876429b2017-04-20 15:46:24 -04003805void Context::getVertexAttribPointerv(GLuint index, GLenum pname, void **pointer)
Jiawei-Shao2597fb62016-12-09 16:38:02 +08003806{
3807 const VertexAttribute &attrib = getGLState().getVertexArray()->getVertexAttribute(index);
3808 QueryVertexAttribPointerv(attrib, pname, pointer);
3809}
3810
Jamie Madillc20ab272016-06-09 07:20:46 -07003811void Context::debugMessageControl(GLenum source,
3812 GLenum type,
3813 GLenum severity,
3814 GLsizei count,
3815 const GLuint *ids,
3816 GLboolean enabled)
3817{
3818 std::vector<GLuint> idVector(ids, ids + count);
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003819 mGLState.getDebug().setMessageControl(source, type, severity, std::move(idVector),
3820 (enabled != GL_FALSE));
Jamie Madillc20ab272016-06-09 07:20:46 -07003821}
3822
3823void Context::debugMessageInsert(GLenum source,
3824 GLenum type,
3825 GLuint id,
3826 GLenum severity,
3827 GLsizei length,
3828 const GLchar *buf)
3829{
3830 std::string msg(buf, (length > 0) ? static_cast<size_t>(length) : strlen(buf));
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003831 mGLState.getDebug().insertMessage(source, type, id, severity, std::move(msg));
Jamie Madillc20ab272016-06-09 07:20:46 -07003832}
3833
3834void Context::debugMessageCallback(GLDEBUGPROCKHR callback, const void *userParam)
3835{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003836 mGLState.getDebug().setCallback(callback, userParam);
Jamie Madillc20ab272016-06-09 07:20:46 -07003837}
3838
3839GLuint Context::getDebugMessageLog(GLuint count,
3840 GLsizei bufSize,
3841 GLenum *sources,
3842 GLenum *types,
3843 GLuint *ids,
3844 GLenum *severities,
3845 GLsizei *lengths,
3846 GLchar *messageLog)
3847{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003848 return static_cast<GLuint>(mGLState.getDebug().getMessages(count, bufSize, sources, types, ids,
3849 severities, lengths, messageLog));
Jamie Madillc20ab272016-06-09 07:20:46 -07003850}
3851
3852void Context::pushDebugGroup(GLenum source, GLuint id, GLsizei length, const GLchar *message)
3853{
3854 std::string msg(message, (length > 0) ? static_cast<size_t>(length) : strlen(message));
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003855 mGLState.getDebug().pushGroup(source, id, std::move(msg));
Jamie Madillc20ab272016-06-09 07:20:46 -07003856}
3857
3858void Context::popDebugGroup()
3859{
Jamie Madilldfde6ab2016-06-09 07:07:18 -07003860 mGLState.getDebug().popGroup();
Jamie Madillc20ab272016-06-09 07:20:46 -07003861}
3862
Jamie Madill876429b2017-04-20 15:46:24 -04003863void Context::bufferData(GLenum target, GLsizeiptr size, const void *data, GLenum usage)
Jamie Madill29639852016-09-02 15:00:09 -04003864{
3865 Buffer *buffer = mGLState.getTargetBuffer(target);
3866 ASSERT(buffer);
Jamie Madillb8353b02017-01-25 12:57:21 -08003867 handleError(buffer->bufferData(this, target, data, size, usage));
Jamie Madill29639852016-09-02 15:00:09 -04003868}
3869
Jamie Madill876429b2017-04-20 15:46:24 -04003870void Context::bufferSubData(GLenum target, GLintptr offset, GLsizeiptr size, const void *data)
Jamie Madill29639852016-09-02 15:00:09 -04003871{
3872 if (data == nullptr)
3873 {
3874 return;
3875 }
3876
3877 Buffer *buffer = mGLState.getTargetBuffer(target);
3878 ASSERT(buffer);
Jamie Madillb8353b02017-01-25 12:57:21 -08003879 handleError(buffer->bufferSubData(this, target, data, size, offset));
Jamie Madill29639852016-09-02 15:00:09 -04003880}
3881
Jamie Madillef300b12016-10-07 15:12:09 -04003882void Context::attachShader(GLuint program, GLuint shader)
3883{
Geoff Lang4ddf5af2016-12-01 14:30:44 -05003884 auto programObject = mState.mShaderPrograms->getProgram(program);
3885 auto shaderObject = mState.mShaderPrograms->getShader(shader);
Jamie Madillef300b12016-10-07 15:12:09 -04003886 ASSERT(programObject && shaderObject);
3887 programObject->attachShader(shaderObject);
3888}
3889
Kenneth Russellf2f6f652016-10-05 19:53:23 -07003890const Workarounds &Context::getWorkarounds() const
3891{
3892 return mWorkarounds;
3893}
3894
Jamie Madillb0817d12016-11-01 15:48:31 -04003895void Context::copyBufferSubData(GLenum readTarget,
3896 GLenum writeTarget,
3897 GLintptr readOffset,
3898 GLintptr writeOffset,
3899 GLsizeiptr size)
3900{
3901 // if size is zero, the copy is a successful no-op
3902 if (size == 0)
3903 {
3904 return;
3905 }
3906
3907 // TODO(jmadill): cache these.
3908 Buffer *readBuffer = mGLState.getTargetBuffer(readTarget);
3909 Buffer *writeBuffer = mGLState.getTargetBuffer(writeTarget);
3910
Jamie Madill5f56ddb2017-01-13 17:29:55 -05003911 handleError(writeBuffer->copyBufferSubData(this, readBuffer, readOffset, writeOffset, size));
Jamie Madillb0817d12016-11-01 15:48:31 -04003912}
3913
Jamie Madill01a80ee2016-11-07 12:06:18 -05003914void Context::bindAttribLocation(GLuint program, GLuint index, const GLchar *name)
3915{
3916 Program *programObject = getProgram(program);
3917 // TODO(jmadill): Re-use this from the validation if possible.
3918 ASSERT(programObject);
3919 programObject->bindAttributeLocation(index, name);
3920}
3921
3922void Context::bindBuffer(GLenum target, GLuint buffer)
3923{
3924 switch (target)
3925 {
3926 case GL_ARRAY_BUFFER:
3927 bindArrayBuffer(buffer);
3928 break;
3929 case GL_ELEMENT_ARRAY_BUFFER:
3930 bindElementArrayBuffer(buffer);
3931 break;
3932 case GL_COPY_READ_BUFFER:
3933 bindCopyReadBuffer(buffer);
3934 break;
3935 case GL_COPY_WRITE_BUFFER:
3936 bindCopyWriteBuffer(buffer);
3937 break;
3938 case GL_PIXEL_PACK_BUFFER:
3939 bindPixelPackBuffer(buffer);
3940 break;
3941 case GL_PIXEL_UNPACK_BUFFER:
3942 bindPixelUnpackBuffer(buffer);
3943 break;
3944 case GL_UNIFORM_BUFFER:
3945 bindGenericUniformBuffer(buffer);
3946 break;
3947 case GL_TRANSFORM_FEEDBACK_BUFFER:
3948 bindGenericTransformFeedbackBuffer(buffer);
3949 break;
Geoff Lang3b573612016-10-31 14:08:10 -04003950 case GL_ATOMIC_COUNTER_BUFFER:
Jiajia Qin6eafb042016-12-27 17:04:07 +08003951 bindGenericAtomicCounterBuffer(buffer);
Geoff Lang3b573612016-10-31 14:08:10 -04003952 break;
3953 case GL_SHADER_STORAGE_BUFFER:
Jiajia Qinf546e7d2017-03-27 14:12:59 +08003954 bindGenericShaderStorageBuffer(buffer);
Geoff Lang3b573612016-10-31 14:08:10 -04003955 break;
3956 case GL_DRAW_INDIRECT_BUFFER:
Jiajia Qin9d7d0b12016-11-29 16:30:31 +08003957 bindDrawIndirectBuffer(buffer);
Geoff Lang3b573612016-10-31 14:08:10 -04003958 break;
3959 case GL_DISPATCH_INDIRECT_BUFFER:
Geoff Lang9f090372016-12-02 10:20:43 -05003960 if (buffer != 0)
3961 {
3962 // Binding buffers to this binding point is not implemented yet.
3963 UNIMPLEMENTED();
3964 }
Geoff Lang3b573612016-10-31 14:08:10 -04003965 break;
Jamie Madill01a80ee2016-11-07 12:06:18 -05003966
3967 default:
3968 UNREACHABLE();
3969 break;
3970 }
3971}
3972
Jiajia Qin6eafb042016-12-27 17:04:07 +08003973void Context::bindBufferBase(GLenum target, GLuint index, GLuint buffer)
3974{
3975 bindBufferRange(target, index, buffer, 0, 0);
3976}
3977
3978void Context::bindBufferRange(GLenum target,
3979 GLuint index,
3980 GLuint buffer,
3981 GLintptr offset,
3982 GLsizeiptr size)
3983{
3984 switch (target)
3985 {
3986 case GL_TRANSFORM_FEEDBACK_BUFFER:
3987 bindIndexedTransformFeedbackBuffer(buffer, index, offset, size);
3988 bindGenericTransformFeedbackBuffer(buffer);
3989 break;
3990 case GL_UNIFORM_BUFFER:
3991 bindIndexedUniformBuffer(buffer, index, offset, size);
3992 bindGenericUniformBuffer(buffer);
3993 break;
3994 case GL_ATOMIC_COUNTER_BUFFER:
3995 bindIndexedAtomicCounterBuffer(buffer, index, offset, size);
3996 bindGenericAtomicCounterBuffer(buffer);
3997 break;
3998 case GL_SHADER_STORAGE_BUFFER:
Jiajia Qinf546e7d2017-03-27 14:12:59 +08003999 bindIndexedShaderStorageBuffer(buffer, index, offset, size);
4000 bindGenericShaderStorageBuffer(buffer);
Jiajia Qin6eafb042016-12-27 17:04:07 +08004001 break;
4002 default:
4003 UNREACHABLE();
4004 break;
4005 }
4006}
4007
Jamie Madill01a80ee2016-11-07 12:06:18 -05004008void Context::bindFramebuffer(GLenum target, GLuint framebuffer)
4009{
4010 if (target == GL_READ_FRAMEBUFFER || target == GL_FRAMEBUFFER)
4011 {
4012 bindReadFramebuffer(framebuffer);
4013 }
4014
4015 if (target == GL_DRAW_FRAMEBUFFER || target == GL_FRAMEBUFFER)
4016 {
4017 bindDrawFramebuffer(framebuffer);
4018 }
4019}
4020
4021void Context::bindRenderbuffer(GLenum target, GLuint renderbuffer)
4022{
4023 ASSERT(target == GL_RENDERBUFFER);
4024 Renderbuffer *object =
Geoff Lang4ddf5af2016-12-01 14:30:44 -05004025 mState.mRenderbuffers->checkRenderbufferAllocation(mImplementation.get(), renderbuffer);
Jamie Madill01a80ee2016-11-07 12:06:18 -05004026 mGLState.setRenderbufferBinding(object);
4027}
4028
JiangYizhoubddc46b2016-12-09 09:50:51 +08004029void Context::texStorage2DMultisample(GLenum target,
4030 GLsizei samples,
4031 GLenum internalformat,
4032 GLsizei width,
4033 GLsizei height,
4034 GLboolean fixedsamplelocations)
4035{
4036 Extents size(width, height, 1);
4037 Texture *texture = getTargetTexture(target);
Jamie Madill8897afa2017-02-06 17:17:23 -05004038 handleError(texture->setStorageMultisample(this, target, samples, internalformat, size,
JiangYizhoubddc46b2016-12-09 09:50:51 +08004039 fixedsamplelocations));
4040}
4041
4042void Context::getMultisamplefv(GLenum pname, GLuint index, GLfloat *val)
4043{
Jamie Madilldd43e6c2017-03-24 14:18:49 -04004044 mGLState.syncDirtyObject(this, GL_READ_FRAMEBUFFER);
JiangYizhoubddc46b2016-12-09 09:50:51 +08004045 const Framebuffer *framebuffer = mGLState.getReadFramebuffer();
4046
4047 switch (pname)
4048 {
4049 case GL_SAMPLE_POSITION:
4050 handleError(framebuffer->getSamplePosition(index, val));
4051 break;
4052 default:
4053 UNREACHABLE();
4054 }
4055}
4056
Jamie Madille8fb6402017-02-14 17:56:40 -05004057void Context::renderbufferStorage(GLenum target,
4058 GLenum internalformat,
4059 GLsizei width,
4060 GLsizei height)
4061{
Jamie Madill4e0e6f82017-02-17 11:06:03 -05004062 // Hack for the special WebGL 1 "DEPTH_STENCIL" internal format.
4063 GLenum convertedInternalFormat = getConvertedRenderbufferFormat(internalformat);
4064
Jamie Madille8fb6402017-02-14 17:56:40 -05004065 Renderbuffer *renderbuffer = mGLState.getCurrentRenderbuffer();
Jamie Madill4e0e6f82017-02-17 11:06:03 -05004066 handleError(renderbuffer->setStorage(convertedInternalFormat, width, height));
Jamie Madille8fb6402017-02-14 17:56:40 -05004067}
4068
4069void Context::renderbufferStorageMultisample(GLenum target,
4070 GLsizei samples,
4071 GLenum internalformat,
4072 GLsizei width,
4073 GLsizei height)
4074{
Jamie Madill4e0e6f82017-02-17 11:06:03 -05004075 // Hack for the special WebGL 1 "DEPTH_STENCIL" internal format.
4076 GLenum convertedInternalFormat = getConvertedRenderbufferFormat(internalformat);
Jamie Madille8fb6402017-02-14 17:56:40 -05004077
4078 Renderbuffer *renderbuffer = mGLState.getCurrentRenderbuffer();
Jamie Madill4e0e6f82017-02-17 11:06:03 -05004079 handleError(
4080 renderbuffer->setStorageMultisample(samples, convertedInternalFormat, width, height));
Jamie Madille8fb6402017-02-14 17:56:40 -05004081}
4082
Geoff Lang38f2cfb2017-04-11 15:23:08 -04004083void Context::getSynciv(GLsync sync, GLenum pname, GLsizei bufSize, GLsizei *length, GLint *values)
4084{
4085 const FenceSync *syncObject = getFenceSync(sync);
Geoff Lang82483b92017-04-11 15:33:00 -04004086 handleError(QuerySynciv(syncObject, pname, bufSize, length, values));
Geoff Lang38f2cfb2017-04-11 15:23:08 -04004087}
4088
JiangYizhoue18e6392017-02-20 10:32:23 +08004089void Context::getFramebufferParameteriv(GLenum target, GLenum pname, GLint *params)
4090{
4091 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
4092 QueryFramebufferParameteriv(framebuffer, pname, params);
4093}
4094
4095void Context::setFramebufferParameteri(GLenum target, GLenum pname, GLint param)
4096{
4097 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
4098 SetFramebufferParameteri(framebuffer, pname, param);
4099}
4100
Jamie Madille14951e2017-03-09 18:55:16 -05004101Error Context::getScratchBuffer(size_t requestedSize, angle::MemoryBuffer **scratchBufferOut) const
4102{
4103 if (!mScratchBuffer.get(requestedSize, scratchBufferOut))
4104 {
Yuly Novikovc4d18aa2017-03-09 18:45:02 -05004105 return OutOfMemory() << "Failed to allocate internal buffer.";
Jamie Madille14951e2017-03-09 18:55:16 -05004106 }
Yuly Novikovc4d18aa2017-03-09 18:45:02 -05004107 return NoError();
Jamie Madille14951e2017-03-09 18:55:16 -05004108}
4109
Xinghua Cao2b396592017-03-29 15:36:04 +08004110void Context::dispatchCompute(GLuint numGroupsX, GLuint numGroupsY, GLuint numGroupsZ)
4111{
4112 if (numGroupsX == 0u || numGroupsY == 0u || numGroupsZ == 0u)
4113 {
4114 return;
4115 }
4116
4117 mImplementation->dispatchCompute(numGroupsX, numGroupsY, numGroupsZ);
4118}
4119
JiangYizhou165361c2017-06-07 14:56:57 +08004120void Context::texStorage2D(GLenum target,
4121 GLsizei levels,
4122 GLenum internalFormat,
4123 GLsizei width,
4124 GLsizei height)
4125{
4126 Extents size(width, height, 1);
4127 Texture *texture = getTargetTexture(target);
4128 handleError(texture->setStorage(this, target, levels, internalFormat, size));
4129}
4130
4131void Context::texStorage3D(GLenum target,
4132 GLsizei levels,
4133 GLenum internalFormat,
4134 GLsizei width,
4135 GLsizei height,
4136 GLsizei depth)
4137{
4138 Extents size(width, height, depth);
4139 Texture *texture = getTargetTexture(target);
4140 handleError(texture->setStorage(this, target, levels, internalFormat, size));
4141}
4142
Jamie Madillc1d770e2017-04-13 17:31:24 -04004143GLenum Context::checkFramebufferStatus(GLenum target)
4144{
4145 Framebuffer *framebuffer = mGLState.getTargetFramebuffer(target);
4146 ASSERT(framebuffer);
4147
4148 return framebuffer->checkStatus(this);
4149}
4150
4151void Context::compileShader(GLuint shader)
4152{
4153 Shader *shaderObject = GetValidShader(this, shader);
4154 if (!shaderObject)
4155 {
4156 return;
4157 }
4158 shaderObject->compile(this);
4159}
4160
4161void Context::deleteBuffers(GLsizei n, const GLuint *buffers)
4162{
4163 for (int i = 0; i < n; i++)
4164 {
4165 deleteBuffer(buffers[i]);
4166 }
4167}
4168
4169void Context::deleteFramebuffers(GLsizei n, const GLuint *framebuffers)
4170{
4171 for (int i = 0; i < n; i++)
4172 {
4173 if (framebuffers[i] != 0)
4174 {
4175 deleteFramebuffer(framebuffers[i]);
4176 }
4177 }
4178}
4179
4180void Context::deleteRenderbuffers(GLsizei n, const GLuint *renderbuffers)
4181{
4182 for (int i = 0; i < n; i++)
4183 {
4184 deleteRenderbuffer(renderbuffers[i]);
4185 }
4186}
4187
4188void Context::deleteTextures(GLsizei n, const GLuint *textures)
4189{
4190 for (int i = 0; i < n; i++)
4191 {
4192 if (textures[i] != 0)
4193 {
4194 deleteTexture(textures[i]);
4195 }
4196 }
4197}
4198
4199void Context::detachShader(GLuint program, GLuint shader)
4200{
4201 Program *programObject = getProgram(program);
4202 ASSERT(programObject);
4203
4204 Shader *shaderObject = getShader(shader);
4205 ASSERT(shaderObject);
4206
4207 programObject->detachShader(this, shaderObject);
4208}
4209
4210void Context::genBuffers(GLsizei n, GLuint *buffers)
4211{
4212 for (int i = 0; i < n; i++)
4213 {
4214 buffers[i] = createBuffer();
4215 }
4216}
4217
4218void Context::genFramebuffers(GLsizei n, GLuint *framebuffers)
4219{
4220 for (int i = 0; i < n; i++)
4221 {
4222 framebuffers[i] = createFramebuffer();
4223 }
4224}
4225
4226void Context::genRenderbuffers(GLsizei n, GLuint *renderbuffers)
4227{
4228 for (int i = 0; i < n; i++)
4229 {
4230 renderbuffers[i] = createRenderbuffer();
4231 }
4232}
4233
4234void Context::genTextures(GLsizei n, GLuint *textures)
4235{
4236 for (int i = 0; i < n; i++)
4237 {
4238 textures[i] = createTexture();
4239 }
4240}
4241
4242void Context::getActiveAttrib(GLuint program,
4243 GLuint index,
4244 GLsizei bufsize,
4245 GLsizei *length,
4246 GLint *size,
4247 GLenum *type,
4248 GLchar *name)
4249{
4250 Program *programObject = getProgram(program);
4251 ASSERT(programObject);
4252 programObject->getActiveAttribute(index, bufsize, length, size, type, name);
4253}
4254
4255void Context::getActiveUniform(GLuint program,
4256 GLuint index,
4257 GLsizei bufsize,
4258 GLsizei *length,
4259 GLint *size,
4260 GLenum *type,
4261 GLchar *name)
4262{
4263 Program *programObject = getProgram(program);
4264 ASSERT(programObject);
4265 programObject->getActiveUniform(index, bufsize, length, size, type, name);
4266}
4267
4268void Context::getAttachedShaders(GLuint program, GLsizei maxcount, GLsizei *count, GLuint *shaders)
4269{
4270 Program *programObject = getProgram(program);
4271 ASSERT(programObject);
4272 programObject->getAttachedShaders(maxcount, count, shaders);
4273}
4274
4275GLint Context::getAttribLocation(GLuint program, const GLchar *name)
4276{
4277 Program *programObject = getProgram(program);
4278 ASSERT(programObject);
4279 return programObject->getAttributeLocation(name);
4280}
4281
4282void Context::getBooleanv(GLenum pname, GLboolean *params)
4283{
4284 GLenum nativeType;
4285 unsigned int numParams = 0;
4286 getQueryParameterInfo(pname, &nativeType, &numParams);
4287
4288 if (nativeType == GL_BOOL)
4289 {
4290 getBooleanvImpl(pname, params);
4291 }
4292 else
4293 {
4294 CastStateValues(this, nativeType, pname, numParams, params);
4295 }
4296}
4297
4298void Context::getFloatv(GLenum pname, GLfloat *params)
4299{
4300 GLenum nativeType;
4301 unsigned int numParams = 0;
4302 getQueryParameterInfo(pname, &nativeType, &numParams);
4303
4304 if (nativeType == GL_FLOAT)
4305 {
4306 getFloatvImpl(pname, params);
4307 }
4308 else
4309 {
4310 CastStateValues(this, nativeType, pname, numParams, params);
4311 }
4312}
4313
4314void Context::getIntegerv(GLenum pname, GLint *params)
4315{
4316 GLenum nativeType;
4317 unsigned int numParams = 0;
4318 getQueryParameterInfo(pname, &nativeType, &numParams);
4319
4320 if (nativeType == GL_INT)
4321 {
4322 getIntegervImpl(pname, params);
4323 }
4324 else
4325 {
4326 CastStateValues(this, nativeType, pname, numParams, params);
4327 }
4328}
4329
4330void Context::getProgramiv(GLuint program, GLenum pname, GLint *params)
4331{
4332 Program *programObject = getProgram(program);
4333 ASSERT(programObject);
4334 QueryProgramiv(programObject, pname, params);
4335}
4336
Jamie Madillbe849e42017-05-02 15:49:00 -04004337void Context::getProgramInfoLog(GLuint program, GLsizei bufsize, GLsizei *length, GLchar *infolog)
Jamie Madillc1d770e2017-04-13 17:31:24 -04004338{
4339 Program *programObject = getProgram(program);
4340 ASSERT(programObject);
4341 programObject->getInfoLog(bufsize, length, infolog);
4342}
4343
4344void Context::getShaderiv(GLuint shader, GLenum pname, GLint *params)
4345{
4346 Shader *shaderObject = getShader(shader);
4347 ASSERT(shaderObject);
Jamie Madillbd044ed2017-06-05 12:59:21 -04004348 QueryShaderiv(this, shaderObject, pname, params);
Jamie Madillc1d770e2017-04-13 17:31:24 -04004349}
4350
4351void Context::getShaderInfoLog(GLuint shader, GLsizei bufsize, GLsizei *length, GLchar *infolog)
4352{
4353 Shader *shaderObject = getShader(shader);
4354 ASSERT(shaderObject);
Jamie Madillbd044ed2017-06-05 12:59:21 -04004355 shaderObject->getInfoLog(this, bufsize, length, infolog);
Jamie Madillc1d770e2017-04-13 17:31:24 -04004356}
4357
4358void Context::getShaderPrecisionFormat(GLenum shadertype,
4359 GLenum precisiontype,
4360 GLint *range,
4361 GLint *precision)
4362{
4363 // TODO(jmadill): Compute shaders.
4364
4365 switch (shadertype)
4366 {
4367 case GL_VERTEX_SHADER:
4368 switch (precisiontype)
4369 {
4370 case GL_LOW_FLOAT:
4371 mCaps.vertexLowpFloat.get(range, precision);
4372 break;
4373 case GL_MEDIUM_FLOAT:
4374 mCaps.vertexMediumpFloat.get(range, precision);
4375 break;
4376 case GL_HIGH_FLOAT:
4377 mCaps.vertexHighpFloat.get(range, precision);
4378 break;
4379
4380 case GL_LOW_INT:
4381 mCaps.vertexLowpInt.get(range, precision);
4382 break;
4383 case GL_MEDIUM_INT:
4384 mCaps.vertexMediumpInt.get(range, precision);
4385 break;
4386 case GL_HIGH_INT:
4387 mCaps.vertexHighpInt.get(range, precision);
4388 break;
4389
4390 default:
4391 UNREACHABLE();
4392 return;
4393 }
4394 break;
4395
4396 case GL_FRAGMENT_SHADER:
4397 switch (precisiontype)
4398 {
4399 case GL_LOW_FLOAT:
4400 mCaps.fragmentLowpFloat.get(range, precision);
4401 break;
4402 case GL_MEDIUM_FLOAT:
4403 mCaps.fragmentMediumpFloat.get(range, precision);
4404 break;
4405 case GL_HIGH_FLOAT:
4406 mCaps.fragmentHighpFloat.get(range, precision);
4407 break;
4408
4409 case GL_LOW_INT:
4410 mCaps.fragmentLowpInt.get(range, precision);
4411 break;
4412 case GL_MEDIUM_INT:
4413 mCaps.fragmentMediumpInt.get(range, precision);
4414 break;
4415 case GL_HIGH_INT:
4416 mCaps.fragmentHighpInt.get(range, precision);
4417 break;
4418
4419 default:
4420 UNREACHABLE();
4421 return;
4422 }
4423 break;
4424
4425 default:
4426 UNREACHABLE();
4427 return;
4428 }
4429}
4430
4431void Context::getShaderSource(GLuint shader, GLsizei bufsize, GLsizei *length, GLchar *source)
4432{
4433 Shader *shaderObject = getShader(shader);
4434 ASSERT(shaderObject);
4435 shaderObject->getSource(bufsize, length, source);
4436}
4437
4438void Context::getUniformfv(GLuint program, GLint location, GLfloat *params)
4439{
4440 Program *programObject = getProgram(program);
4441 ASSERT(programObject);
4442 programObject->getUniformfv(location, params);
4443}
4444
4445void Context::getUniformiv(GLuint program, GLint location, GLint *params)
4446{
4447 Program *programObject = getProgram(program);
4448 ASSERT(programObject);
4449 programObject->getUniformiv(location, params);
4450}
4451
4452GLint Context::getUniformLocation(GLuint program, const GLchar *name)
4453{
4454 Program *programObject = getProgram(program);
4455 ASSERT(programObject);
4456 return programObject->getUniformLocation(name);
4457}
4458
4459GLboolean Context::isBuffer(GLuint buffer)
4460{
4461 if (buffer == 0)
4462 {
4463 return GL_FALSE;
4464 }
4465
4466 return (getBuffer(buffer) ? GL_TRUE : GL_FALSE);
4467}
4468
4469GLboolean Context::isEnabled(GLenum cap)
4470{
4471 return mGLState.getEnableFeature(cap);
4472}
4473
4474GLboolean Context::isFramebuffer(GLuint framebuffer)
4475{
4476 if (framebuffer == 0)
4477 {
4478 return GL_FALSE;
4479 }
4480
4481 return (getFramebuffer(framebuffer) ? GL_TRUE : GL_FALSE);
4482}
4483
4484GLboolean Context::isProgram(GLuint program)
4485{
4486 if (program == 0)
4487 {
4488 return GL_FALSE;
4489 }
4490
4491 return (getProgram(program) ? GL_TRUE : GL_FALSE);
4492}
4493
4494GLboolean Context::isRenderbuffer(GLuint renderbuffer)
4495{
4496 if (renderbuffer == 0)
4497 {
4498 return GL_FALSE;
4499 }
4500
4501 return (getRenderbuffer(renderbuffer) ? GL_TRUE : GL_FALSE);
4502}
4503
4504GLboolean Context::isShader(GLuint shader)
4505{
4506 if (shader == 0)
4507 {
4508 return GL_FALSE;
4509 }
4510
4511 return (getShader(shader) ? GL_TRUE : GL_FALSE);
4512}
4513
4514GLboolean Context::isTexture(GLuint texture)
4515{
4516 if (texture == 0)
4517 {
4518 return GL_FALSE;
4519 }
4520
4521 return (getTexture(texture) ? GL_TRUE : GL_FALSE);
4522}
4523
4524void Context::linkProgram(GLuint program)
4525{
4526 Program *programObject = getProgram(program);
4527 ASSERT(programObject);
4528 handleError(programObject->link(this));
4529}
4530
4531void Context::releaseShaderCompiler()
4532{
Jamie Madill2f348d22017-06-05 10:50:59 -04004533 mCompiler.set(nullptr);
Jamie Madillc1d770e2017-04-13 17:31:24 -04004534}
4535
4536void Context::shaderBinary(GLsizei n,
4537 const GLuint *shaders,
4538 GLenum binaryformat,
Jamie Madill876429b2017-04-20 15:46:24 -04004539 const void *binary,
Jamie Madillc1d770e2017-04-13 17:31:24 -04004540 GLsizei length)
4541{
4542 // No binary shader formats are supported.
4543 UNIMPLEMENTED();
4544}
4545
4546void Context::shaderSource(GLuint shader,
4547 GLsizei count,
4548 const GLchar *const *string,
4549 const GLint *length)
4550{
4551 Shader *shaderObject = getShader(shader);
4552 ASSERT(shaderObject);
4553 shaderObject->setSource(count, string, length);
4554}
4555
4556void Context::stencilFunc(GLenum func, GLint ref, GLuint mask)
4557{
4558 stencilFuncSeparate(GL_FRONT_AND_BACK, func, ref, mask);
4559}
4560
4561void Context::stencilMask(GLuint mask)
4562{
4563 stencilMaskSeparate(GL_FRONT_AND_BACK, mask);
4564}
4565
4566void Context::stencilOp(GLenum fail, GLenum zfail, GLenum zpass)
4567{
4568 stencilOpSeparate(GL_FRONT_AND_BACK, fail, zfail, zpass);
4569}
4570
4571void Context::uniform1f(GLint location, GLfloat x)
4572{
4573 Program *program = mGLState.getProgram();
4574 program->setUniform1fv(location, 1, &x);
4575}
4576
4577void Context::uniform1fv(GLint location, GLsizei count, const GLfloat *v)
4578{
4579 Program *program = mGLState.getProgram();
4580 program->setUniform1fv(location, count, v);
4581}
4582
4583void Context::uniform1i(GLint location, GLint x)
4584{
4585 Program *program = mGLState.getProgram();
4586 program->setUniform1iv(location, 1, &x);
4587}
4588
4589void Context::uniform1iv(GLint location, GLsizei count, const GLint *v)
4590{
4591 Program *program = mGLState.getProgram();
4592 program->setUniform1iv(location, count, v);
4593}
4594
4595void Context::uniform2f(GLint location, GLfloat x, GLfloat y)
4596{
4597 GLfloat xy[2] = {x, y};
4598 Program *program = mGLState.getProgram();
4599 program->setUniform2fv(location, 1, xy);
4600}
4601
4602void Context::uniform2fv(GLint location, GLsizei count, const GLfloat *v)
4603{
4604 Program *program = mGLState.getProgram();
4605 program->setUniform2fv(location, count, v);
4606}
4607
4608void Context::uniform2i(GLint location, GLint x, GLint y)
4609{
4610 GLint xy[2] = {x, y};
4611 Program *program = mGLState.getProgram();
4612 program->setUniform2iv(location, 1, xy);
4613}
4614
4615void Context::uniform2iv(GLint location, GLsizei count, const GLint *v)
4616{
4617 Program *program = mGLState.getProgram();
4618 program->setUniform2iv(location, count, v);
4619}
4620
4621void Context::uniform3f(GLint location, GLfloat x, GLfloat y, GLfloat z)
4622{
4623 GLfloat xyz[3] = {x, y, z};
4624 Program *program = mGLState.getProgram();
4625 program->setUniform3fv(location, 1, xyz);
4626}
4627
4628void Context::uniform3fv(GLint location, GLsizei count, const GLfloat *v)
4629{
4630 Program *program = mGLState.getProgram();
4631 program->setUniform3fv(location, count, v);
4632}
4633
4634void Context::uniform3i(GLint location, GLint x, GLint y, GLint z)
4635{
4636 GLint xyz[3] = {x, y, z};
4637 Program *program = mGLState.getProgram();
4638 program->setUniform3iv(location, 1, xyz);
4639}
4640
4641void Context::uniform3iv(GLint location, GLsizei count, const GLint *v)
4642{
4643 Program *program = mGLState.getProgram();
4644 program->setUniform3iv(location, count, v);
4645}
4646
4647void Context::uniform4f(GLint location, GLfloat x, GLfloat y, GLfloat z, GLfloat w)
4648{
4649 GLfloat xyzw[4] = {x, y, z, w};
4650 Program *program = mGLState.getProgram();
4651 program->setUniform4fv(location, 1, xyzw);
4652}
4653
4654void Context::uniform4fv(GLint location, GLsizei count, const GLfloat *v)
4655{
4656 Program *program = mGLState.getProgram();
4657 program->setUniform4fv(location, count, v);
4658}
4659
4660void Context::uniform4i(GLint location, GLint x, GLint y, GLint z, GLint w)
4661{
4662 GLint xyzw[4] = {x, y, z, w};
4663 Program *program = mGLState.getProgram();
4664 program->setUniform4iv(location, 1, xyzw);
4665}
4666
4667void Context::uniform4iv(GLint location, GLsizei count, const GLint *v)
4668{
4669 Program *program = mGLState.getProgram();
4670 program->setUniform4iv(location, count, v);
4671}
4672
4673void Context::uniformMatrix2fv(GLint location,
4674 GLsizei count,
4675 GLboolean transpose,
4676 const GLfloat *value)
4677{
4678 Program *program = mGLState.getProgram();
4679 program->setUniformMatrix2fv(location, count, transpose, value);
4680}
4681
4682void Context::uniformMatrix3fv(GLint location,
4683 GLsizei count,
4684 GLboolean transpose,
4685 const GLfloat *value)
4686{
4687 Program *program = mGLState.getProgram();
4688 program->setUniformMatrix3fv(location, count, transpose, value);
4689}
4690
4691void Context::uniformMatrix4fv(GLint location,
4692 GLsizei count,
4693 GLboolean transpose,
4694 const GLfloat *value)
4695{
4696 Program *program = mGLState.getProgram();
4697 program->setUniformMatrix4fv(location, count, transpose, value);
4698}
4699
4700void Context::validateProgram(GLuint program)
4701{
4702 Program *programObject = getProgram(program);
4703 ASSERT(programObject);
4704 programObject->validate(mCaps);
4705}
4706
Jamie Madilld04908b2017-06-09 14:15:35 -04004707void Context::getProgramBinary(GLuint program,
4708 GLsizei bufSize,
4709 GLsizei *length,
4710 GLenum *binaryFormat,
4711 void *binary)
4712{
4713 Program *programObject = getProgram(program);
4714 ASSERT(programObject != nullptr);
4715
4716 handleError(programObject->saveBinary(this, binaryFormat, binary, bufSize, length));
4717}
4718
4719void Context::programBinary(GLuint program, GLenum binaryFormat, const void *binary, GLsizei length)
4720{
4721 Program *programObject = getProgram(program);
4722 ASSERT(programObject != nullptr);
4723
4724 handleError(programObject->loadBinary(this, binaryFormat, binary, length));
4725}
4726
Jamie Madillc29968b2016-01-20 11:17:23 -05004727} // namespace gl