blob: 2b3863f6954ad637adfe8d06b43aeefcda5186ce [file] [log] [blame]
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001//
daniel@transgaming.com8ca9c6e2012-01-27 15:38:54 +00002// Copyright (c) 2002-2012 The ANGLE Project Authors. All rights reserved.
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +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// libGLESv2.cpp: Implements the exported OpenGL ES 2.0 functions.
8
9#define GL_APICALL
10#include <GLES2/gl2.h>
11#include <GLES2/gl2ext.h>
12
daniel@transgaming.com00c75962010-03-11 20:36:15 +000013#include <exception>
14#include <limits>
15
alokp@chromium.orgea0e1af2010-03-22 19:33:14 +000016#include "common/debug.h"
daniel@transgaming.coma0ce7e62011-01-25 14:47:16 +000017#include "common/version.h"
daniel@transgaming.combbf56f72010-04-20 18:52:13 +000018
19#include "libGLESv2/main.h"
20#include "libGLESv2/mathutil.h"
21#include "libGLESv2/utilities.h"
22#include "libGLESv2/Buffer.h"
23#include "libGLESv2/Context.h"
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +000024#include "libGLESv2/Fence.h"
daniel@transgaming.combbf56f72010-04-20 18:52:13 +000025#include "libGLESv2/Framebuffer.h"
26#include "libGLESv2/Program.h"
27#include "libGLESv2/Renderbuffer.h"
28#include "libGLESv2/Shader.h"
29#include "libGLESv2/Texture.h"
daniel@transgaming.com86bdb822012-01-20 18:24:39 +000030#include "libGLESv2/Query.h"
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000031
daniel@transgaming.com4f9ef0d2011-05-30 23:51:19 +000032bool validImageSize(GLint level, GLsizei width, GLsizei height)
33{
34 if (level < 0 || width < 0 || height < 0)
35 {
36 return false;
37 }
38
39 if (gl::getContext() && gl::getContext()->supportsNonPower2Texture())
40 {
41 return true;
42 }
43
44 if (level == 0)
45 {
46 return true;
47 }
48
49 if (gl::isPow2(width) && gl::isPow2(height))
50 {
51 return true;
52 }
53
54 return false;
55}
56
daniel@transgaming.com343373a2011-11-29 19:42:32 +000057bool validateSubImageParams(bool compressed, GLsizei width, GLsizei height, GLint xoffset, GLint yoffset, GLint level, GLenum format, gl::Texture *texture)
58{
59 if (!texture)
60 {
61 return error(GL_INVALID_OPERATION, false);
62 }
63
64 if (compressed != texture->isCompressed())
65 {
66 return error(GL_INVALID_OPERATION, false);
67 }
68
69 if (format != GL_NONE && format != texture->getInternalFormat())
70 {
71 return error(GL_INVALID_OPERATION, false);
72 }
73
74 if (compressed)
75 {
76 if ((width % 4 != 0 && width != texture->getWidth(0)) ||
77 (height % 4 != 0 && height != texture->getHeight(0)))
78 {
79 return error(GL_INVALID_OPERATION, false);
80 }
81 }
82
83 if (xoffset + width > texture->getWidth(level) ||
84 yoffset + height > texture->getHeight(level))
85 {
86 return error(GL_INVALID_VALUE, false);
87 }
88
89 return true;
90}
91
daniel@transgaming.comb7915a52011-11-12 03:14:20 +000092// check for combinations of format and type that are valid for ReadPixels
93bool validReadFormatType(GLenum format, GLenum type)
94{
95 switch (format)
96 {
97 case GL_RGBA:
98 switch (type)
99 {
100 case GL_UNSIGNED_BYTE:
101 break;
102 default:
103 return false;
104 }
105 break;
106 case GL_BGRA_EXT:
107 switch (type)
108 {
109 case GL_UNSIGNED_BYTE:
110 case GL_UNSIGNED_SHORT_4_4_4_4_REV_EXT:
111 case GL_UNSIGNED_SHORT_1_5_5_5_REV_EXT:
112 break;
113 default:
114 return false;
115 }
116 break;
117 case gl::IMPLEMENTATION_COLOR_READ_FORMAT:
118 switch (type)
119 {
120 case gl::IMPLEMENTATION_COLOR_READ_TYPE:
121 break;
122 default:
123 return false;
124 }
125 break;
126 default:
127 return false;
128 }
129 return true;
130}
131
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000132extern "C"
133{
134
135void __stdcall glActiveTexture(GLenum texture)
136{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000137 EVENT("(GLenum texture = 0x%X)", texture);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000138
139 try
140 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000141 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000142
143 if (context)
144 {
daniel@transgaming.com3f74c7a2011-05-11 15:36:51 +0000145 if (texture < GL_TEXTURE0 || texture > GL_TEXTURE0 + context->getMaximumCombinedTextureImageUnits() - 1)
146 {
147 return error(GL_INVALID_ENUM);
148 }
149
daniel@transgaming.com428d1582010-05-04 03:35:25 +0000150 context->setActiveSampler(texture - GL_TEXTURE0);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000151 }
152 }
153 catch(std::bad_alloc&)
154 {
155 return error(GL_OUT_OF_MEMORY);
156 }
157}
158
159void __stdcall glAttachShader(GLuint program, GLuint shader)
160{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000161 EVENT("(GLuint program = %d, GLuint shader = %d)", program, shader);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000162
163 try
164 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000165 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000166
167 if (context)
168 {
169 gl::Program *programObject = context->getProgram(program);
170 gl::Shader *shaderObject = context->getShader(shader);
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +0000171
daniel@transgaming.come9d6ed02010-04-13 03:26:23 +0000172 if (!programObject)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000173 {
daniel@transgaming.come9d6ed02010-04-13 03:26:23 +0000174 if (context->getShader(program))
175 {
176 return error(GL_INVALID_OPERATION);
177 }
178 else
179 {
180 return error(GL_INVALID_VALUE);
181 }
182 }
183
184 if (!shaderObject)
185 {
186 if (context->getProgram(shader))
187 {
188 return error(GL_INVALID_OPERATION);
189 }
190 else
191 {
192 return error(GL_INVALID_VALUE);
193 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000194 }
195
196 if (!programObject->attachShader(shaderObject))
197 {
198 return error(GL_INVALID_OPERATION);
199 }
200 }
201 }
202 catch(std::bad_alloc&)
203 {
204 return error(GL_OUT_OF_MEMORY);
205 }
206}
207
daniel@transgaming.com86bdb822012-01-20 18:24:39 +0000208void __stdcall glBeginQueryEXT(GLenum target, GLuint id)
209{
210 EVENT("(GLenum target = 0x%X, GLuint %d)", target, id);
211
212 try
213 {
214 switch (target)
215 {
216 case GL_ANY_SAMPLES_PASSED_EXT:
217 case GL_ANY_SAMPLES_PASSED_CONSERVATIVE_EXT:
218 break;
219 default:
220 return error(GL_INVALID_ENUM);
221 }
222
223 if (id == 0)
224 {
225 return error(GL_INVALID_OPERATION);
226 }
227
228 gl::Context *context = gl::getNonLostContext();
229
230 if (context)
231 {
232 context->beginQuery(target, id);
233 }
234 }
235 catch(std::bad_alloc&)
236 {
237 return error(GL_OUT_OF_MEMORY);
238 }
239}
240
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +0000241void __stdcall glBindAttribLocation(GLuint program, GLuint index, const GLchar* name)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000242{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000243 EVENT("(GLuint program = %d, GLuint index = %d, const GLchar* name = 0x%0.8p)", program, index, name);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000244
245 try
246 {
247 if (index >= gl::MAX_VERTEX_ATTRIBS)
248 {
249 return error(GL_INVALID_VALUE);
250 }
251
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000252 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000253
254 if (context)
255 {
256 gl::Program *programObject = context->getProgram(program);
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +0000257
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000258 if (!programObject)
259 {
daniel@transgaming.com98079832010-04-13 03:26:29 +0000260 if (context->getShader(program))
261 {
262 return error(GL_INVALID_OPERATION);
263 }
264 else
265 {
266 return error(GL_INVALID_VALUE);
267 }
268 }
269
270 if (strncmp(name, "gl_", 3) == 0)
271 {
272 return error(GL_INVALID_OPERATION);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000273 }
274
275 programObject->bindAttributeLocation(index, name);
276 }
277 }
278 catch(std::bad_alloc&)
279 {
280 return error(GL_OUT_OF_MEMORY);
281 }
282}
283
284void __stdcall glBindBuffer(GLenum target, GLuint buffer)
285{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000286 EVENT("(GLenum target = 0x%X, GLuint buffer = %d)", target, buffer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000287
288 try
289 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000290 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000291
292 if (context)
293 {
294 switch (target)
295 {
296 case GL_ARRAY_BUFFER:
297 context->bindArrayBuffer(buffer);
298 return;
299 case GL_ELEMENT_ARRAY_BUFFER:
300 context->bindElementArrayBuffer(buffer);
301 return;
302 default:
303 return error(GL_INVALID_ENUM);
304 }
305 }
306 }
307 catch(std::bad_alloc&)
308 {
309 return error(GL_OUT_OF_MEMORY);
310 }
311}
312
313void __stdcall glBindFramebuffer(GLenum target, GLuint framebuffer)
314{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000315 EVENT("(GLenum target = 0x%X, GLuint framebuffer = %d)", target, framebuffer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000316
317 try
318 {
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +0000319 if (target != GL_FRAMEBUFFER && target != GL_DRAW_FRAMEBUFFER_ANGLE && target != GL_READ_FRAMEBUFFER_ANGLE)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000320 {
321 return error(GL_INVALID_ENUM);
322 }
323
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000324 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000325
326 if (context)
327 {
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +0000328 if (target == GL_READ_FRAMEBUFFER_ANGLE || target == GL_FRAMEBUFFER)
329 {
330 context->bindReadFramebuffer(framebuffer);
331 }
332
333 if (target == GL_DRAW_FRAMEBUFFER_ANGLE || target == GL_FRAMEBUFFER)
334 {
335 context->bindDrawFramebuffer(framebuffer);
336 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000337 }
338 }
339 catch(std::bad_alloc&)
340 {
341 return error(GL_OUT_OF_MEMORY);
342 }
343}
344
345void __stdcall glBindRenderbuffer(GLenum target, GLuint renderbuffer)
346{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000347 EVENT("(GLenum target = 0x%X, GLuint renderbuffer = %d)", target, renderbuffer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000348
349 try
350 {
351 if (target != GL_RENDERBUFFER)
352 {
353 return error(GL_INVALID_ENUM);
354 }
355
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000356 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000357
358 if (context)
359 {
360 context->bindRenderbuffer(renderbuffer);
361 }
362 }
363 catch(std::bad_alloc&)
364 {
365 return error(GL_OUT_OF_MEMORY);
366 }
367}
368
369void __stdcall glBindTexture(GLenum target, GLuint texture)
370{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000371 EVENT("(GLenum target = 0x%X, GLuint texture = %d)", target, texture);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000372
373 try
374 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000375 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000376
377 if (context)
378 {
379 gl::Texture *textureObject = context->getTexture(texture);
380
381 if (textureObject && textureObject->getTarget() != target && texture != 0)
382 {
383 return error(GL_INVALID_OPERATION);
384 }
385
386 switch (target)
387 {
388 case GL_TEXTURE_2D:
389 context->bindTexture2D(texture);
390 return;
391 case GL_TEXTURE_CUBE_MAP:
392 context->bindTextureCubeMap(texture);
393 return;
394 default:
395 return error(GL_INVALID_ENUM);
396 }
397 }
398 }
399 catch(std::bad_alloc&)
400 {
401 return error(GL_OUT_OF_MEMORY);
402 }
403}
404
405void __stdcall glBlendColor(GLclampf red, GLclampf green, GLclampf blue, GLclampf alpha)
406{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000407 EVENT("(GLclampf red = %f, GLclampf green = %f, GLclampf blue = %f, GLclampf alpha = %f)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000408 red, green, blue, alpha);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000409
410 try
411 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000412 gl::Context* context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000413
414 if (context)
415 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +0000416 context->setBlendColor(gl::clamp01(red), gl::clamp01(green), gl::clamp01(blue), gl::clamp01(alpha));
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000417 }
418 }
419 catch(std::bad_alloc&)
420 {
421 return error(GL_OUT_OF_MEMORY);
422 }
423}
424
425void __stdcall glBlendEquation(GLenum mode)
426{
427 glBlendEquationSeparate(mode, mode);
428}
429
430void __stdcall glBlendEquationSeparate(GLenum modeRGB, GLenum modeAlpha)
431{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000432 EVENT("(GLenum modeRGB = 0x%X, GLenum modeAlpha = 0x%X)", modeRGB, modeAlpha);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000433
434 try
435 {
436 switch (modeRGB)
437 {
438 case GL_FUNC_ADD:
439 case GL_FUNC_SUBTRACT:
440 case GL_FUNC_REVERSE_SUBTRACT:
441 break;
442 default:
443 return error(GL_INVALID_ENUM);
444 }
445
446 switch (modeAlpha)
447 {
448 case GL_FUNC_ADD:
449 case GL_FUNC_SUBTRACT:
450 case GL_FUNC_REVERSE_SUBTRACT:
451 break;
452 default:
453 return error(GL_INVALID_ENUM);
454 }
455
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000456 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000457
458 if (context)
459 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +0000460 context->setBlendEquation(modeRGB, modeAlpha);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000461 }
462 }
463 catch(std::bad_alloc&)
464 {
465 return error(GL_OUT_OF_MEMORY);
466 }
467}
468
469void __stdcall glBlendFunc(GLenum sfactor, GLenum dfactor)
470{
471 glBlendFuncSeparate(sfactor, dfactor, sfactor, dfactor);
472}
473
474void __stdcall glBlendFuncSeparate(GLenum srcRGB, GLenum dstRGB, GLenum srcAlpha, GLenum dstAlpha)
475{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000476 EVENT("(GLenum srcRGB = 0x%X, GLenum dstRGB = 0x%X, GLenum srcAlpha = 0x%X, GLenum dstAlpha = 0x%X)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000477 srcRGB, dstRGB, srcAlpha, dstAlpha);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000478
479 try
480 {
481 switch (srcRGB)
482 {
483 case GL_ZERO:
484 case GL_ONE:
485 case GL_SRC_COLOR:
486 case GL_ONE_MINUS_SRC_COLOR:
487 case GL_DST_COLOR:
488 case GL_ONE_MINUS_DST_COLOR:
489 case GL_SRC_ALPHA:
490 case GL_ONE_MINUS_SRC_ALPHA:
491 case GL_DST_ALPHA:
492 case GL_ONE_MINUS_DST_ALPHA:
493 case GL_CONSTANT_COLOR:
494 case GL_ONE_MINUS_CONSTANT_COLOR:
495 case GL_CONSTANT_ALPHA:
496 case GL_ONE_MINUS_CONSTANT_ALPHA:
497 case GL_SRC_ALPHA_SATURATE:
498 break;
499 default:
500 return error(GL_INVALID_ENUM);
501 }
502
503 switch (dstRGB)
504 {
505 case GL_ZERO:
506 case GL_ONE:
507 case GL_SRC_COLOR:
508 case GL_ONE_MINUS_SRC_COLOR:
509 case GL_DST_COLOR:
510 case GL_ONE_MINUS_DST_COLOR:
511 case GL_SRC_ALPHA:
512 case GL_ONE_MINUS_SRC_ALPHA:
513 case GL_DST_ALPHA:
514 case GL_ONE_MINUS_DST_ALPHA:
515 case GL_CONSTANT_COLOR:
516 case GL_ONE_MINUS_CONSTANT_COLOR:
517 case GL_CONSTANT_ALPHA:
518 case GL_ONE_MINUS_CONSTANT_ALPHA:
519 break;
520 default:
521 return error(GL_INVALID_ENUM);
522 }
523
524 switch (srcAlpha)
525 {
526 case GL_ZERO:
527 case GL_ONE:
528 case GL_SRC_COLOR:
529 case GL_ONE_MINUS_SRC_COLOR:
530 case GL_DST_COLOR:
531 case GL_ONE_MINUS_DST_COLOR:
532 case GL_SRC_ALPHA:
533 case GL_ONE_MINUS_SRC_ALPHA:
534 case GL_DST_ALPHA:
535 case GL_ONE_MINUS_DST_ALPHA:
536 case GL_CONSTANT_COLOR:
537 case GL_ONE_MINUS_CONSTANT_COLOR:
538 case GL_CONSTANT_ALPHA:
539 case GL_ONE_MINUS_CONSTANT_ALPHA:
540 case GL_SRC_ALPHA_SATURATE:
541 break;
542 default:
543 return error(GL_INVALID_ENUM);
544 }
545
546 switch (dstAlpha)
547 {
548 case GL_ZERO:
549 case GL_ONE:
550 case GL_SRC_COLOR:
551 case GL_ONE_MINUS_SRC_COLOR:
552 case GL_DST_COLOR:
553 case GL_ONE_MINUS_DST_COLOR:
554 case GL_SRC_ALPHA:
555 case GL_ONE_MINUS_SRC_ALPHA:
556 case GL_DST_ALPHA:
557 case GL_ONE_MINUS_DST_ALPHA:
558 case GL_CONSTANT_COLOR:
559 case GL_ONE_MINUS_CONSTANT_COLOR:
560 case GL_CONSTANT_ALPHA:
561 case GL_ONE_MINUS_CONSTANT_ALPHA:
562 break;
563 default:
564 return error(GL_INVALID_ENUM);
565 }
566
daniel@transgaming.comfe453652010-03-16 06:23:28 +0000567 bool constantColorUsed = (srcRGB == GL_CONSTANT_COLOR || srcRGB == GL_ONE_MINUS_CONSTANT_COLOR ||
568 dstRGB == GL_CONSTANT_COLOR || dstRGB == GL_ONE_MINUS_CONSTANT_COLOR);
569
570 bool constantAlphaUsed = (srcRGB == GL_CONSTANT_ALPHA || srcRGB == GL_ONE_MINUS_CONSTANT_ALPHA ||
571 dstRGB == GL_CONSTANT_ALPHA || dstRGB == GL_ONE_MINUS_CONSTANT_ALPHA);
572
573 if (constantColorUsed && constantAlphaUsed)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000574 {
daniel@transgaming.comfe453652010-03-16 06:23:28 +0000575 ERR("Simultaneous use of GL_CONSTANT_ALPHA/GL_ONE_MINUS_CONSTANT_ALPHA and GL_CONSTANT_COLOR/GL_ONE_MINUS_CONSTANT_COLOR invalid under WebGL");
576 return error(GL_INVALID_OPERATION);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000577 }
578
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000579 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000580
581 if (context)
582 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +0000583 context->setBlendFactors(srcRGB, dstRGB, srcAlpha, dstAlpha);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000584 }
585 }
586 catch(std::bad_alloc&)
587 {
588 return error(GL_OUT_OF_MEMORY);
589 }
590}
591
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +0000592void __stdcall glBufferData(GLenum target, GLsizeiptr size, const GLvoid* data, GLenum usage)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000593{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000594 EVENT("(GLenum target = 0x%X, GLsizeiptr size = %d, const GLvoid* data = 0x%0.8p, GLenum usage = %d)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000595 target, size, data, usage);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000596
597 try
598 {
599 if (size < 0)
600 {
601 return error(GL_INVALID_VALUE);
602 }
603
604 switch (usage)
605 {
606 case GL_STREAM_DRAW:
607 case GL_STATIC_DRAW:
608 case GL_DYNAMIC_DRAW:
609 break;
610 default:
611 return error(GL_INVALID_ENUM);
612 }
613
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000614 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000615
616 if (context)
617 {
618 gl::Buffer *buffer;
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +0000619
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000620 switch (target)
621 {
622 case GL_ARRAY_BUFFER:
623 buffer = context->getArrayBuffer();
624 break;
625 case GL_ELEMENT_ARRAY_BUFFER:
626 buffer = context->getElementArrayBuffer();
627 break;
628 default:
629 return error(GL_INVALID_ENUM);
630 }
631
632 if (!buffer)
633 {
634 return error(GL_INVALID_OPERATION);
635 }
636
daniel@transgaming.com0f7aaf52010-03-11 19:41:38 +0000637 buffer->bufferData(data, size, usage);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000638 }
639 }
640 catch(std::bad_alloc&)
641 {
642 return error(GL_OUT_OF_MEMORY);
643 }
644}
645
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +0000646void __stdcall glBufferSubData(GLenum target, GLintptr offset, GLsizeiptr size, const GLvoid* data)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000647{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000648 EVENT("(GLenum target = 0x%X, GLintptr offset = %d, GLsizeiptr size = %d, const GLvoid* data = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000649 target, offset, size, data);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000650
651 try
652 {
daniel@transgaming.comdefa1c32010-05-18 18:51:45 +0000653 if (size < 0 || offset < 0)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000654 {
655 return error(GL_INVALID_VALUE);
656 }
657
daniel@transgaming.comd4620a32010-03-21 04:31:28 +0000658 if (data == NULL)
659 {
660 return;
661 }
662
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000663 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com0f7aaf52010-03-11 19:41:38 +0000664
665 if (context)
666 {
667 gl::Buffer *buffer;
668
669 switch (target)
670 {
671 case GL_ARRAY_BUFFER:
672 buffer = context->getArrayBuffer();
673 break;
674 case GL_ELEMENT_ARRAY_BUFFER:
675 buffer = context->getElementArrayBuffer();
676 break;
677 default:
678 return error(GL_INVALID_ENUM);
679 }
680
681 if (!buffer)
682 {
683 return error(GL_INVALID_OPERATION);
684 }
685
daniel@transgaming.comdefa1c32010-05-18 18:51:45 +0000686 if ((size_t)size + offset > buffer->size())
daniel@transgaming.com0f7aaf52010-03-11 19:41:38 +0000687 {
daniel@transgaming.comdefa1c32010-05-18 18:51:45 +0000688 return error(GL_INVALID_VALUE);
daniel@transgaming.com0f7aaf52010-03-11 19:41:38 +0000689 }
daniel@transgaming.comdefa1c32010-05-18 18:51:45 +0000690
691 buffer->bufferSubData(data, size, offset);
daniel@transgaming.com0f7aaf52010-03-11 19:41:38 +0000692 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000693 }
694 catch(std::bad_alloc&)
695 {
696 return error(GL_OUT_OF_MEMORY);
697 }
698}
699
700GLenum __stdcall glCheckFramebufferStatus(GLenum target)
701{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000702 EVENT("(GLenum target = 0x%X)", target);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000703
704 try
705 {
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +0000706 if (target != GL_FRAMEBUFFER && target != GL_DRAW_FRAMEBUFFER_ANGLE && target != GL_READ_FRAMEBUFFER_ANGLE)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000707 {
708 return error(GL_INVALID_ENUM, 0);
709 }
710
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000711 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000712
713 if (context)
714 {
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +0000715 gl::Framebuffer *framebuffer = NULL;
716 if (target == GL_READ_FRAMEBUFFER_ANGLE)
717 {
718 framebuffer = context->getReadFramebuffer();
719 }
720 else
721 {
722 framebuffer = context->getDrawFramebuffer();
723 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000724
725 return framebuffer->completeness();
726 }
727 }
728 catch(std::bad_alloc&)
729 {
730 return error(GL_OUT_OF_MEMORY, 0);
731 }
732
733 return 0;
734}
735
736void __stdcall glClear(GLbitfield mask)
737{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000738 EVENT("(GLbitfield mask = %X)", mask);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000739
740 try
741 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000742 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000743
744 if (context)
745 {
746 context->clear(mask);
747 }
748 }
749 catch(std::bad_alloc&)
750 {
751 return error(GL_OUT_OF_MEMORY);
752 }
753}
754
755void __stdcall glClearColor(GLclampf red, GLclampf green, GLclampf blue, GLclampf alpha)
756{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000757 EVENT("(GLclampf red = %f, GLclampf green = %f, GLclampf blue = %f, GLclampf alpha = %f)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000758 red, green, blue, alpha);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000759
760 try
761 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000762 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000763
764 if (context)
765 {
766 context->setClearColor(red, green, blue, alpha);
767 }
768 }
769 catch(std::bad_alloc&)
770 {
771 return error(GL_OUT_OF_MEMORY);
772 }
773}
774
775void __stdcall glClearDepthf(GLclampf depth)
776{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000777 EVENT("(GLclampf depth = %f)", depth);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000778
779 try
780 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000781 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000782
783 if (context)
784 {
785 context->setClearDepth(depth);
786 }
787 }
788 catch(std::bad_alloc&)
789 {
790 return error(GL_OUT_OF_MEMORY);
791 }
792}
793
794void __stdcall glClearStencil(GLint s)
795{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000796 EVENT("(GLint s = %d)", s);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000797
798 try
799 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000800 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000801
802 if (context)
803 {
804 context->setClearStencil(s);
805 }
806 }
807 catch(std::bad_alloc&)
808 {
809 return error(GL_OUT_OF_MEMORY);
810 }
811}
812
813void __stdcall glColorMask(GLboolean red, GLboolean green, GLboolean blue, GLboolean alpha)
814{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000815 EVENT("(GLboolean red = %d, GLboolean green = %d, GLboolean blue = %d, GLboolean alpha = %d)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000816 red, green, blue, alpha);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000817
818 try
819 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000820 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000821
822 if (context)
823 {
daniel@transgaming.coma36f98e2010-05-18 18:51:09 +0000824 context->setColorMask(red == GL_TRUE, green == GL_TRUE, blue == GL_TRUE, alpha == GL_TRUE);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000825 }
826 }
827 catch(std::bad_alloc&)
828 {
829 return error(GL_OUT_OF_MEMORY);
830 }
831}
832
833void __stdcall glCompileShader(GLuint shader)
834{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000835 EVENT("(GLuint shader = %d)", shader);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000836
837 try
838 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000839 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000840
841 if (context)
842 {
843 gl::Shader *shaderObject = context->getShader(shader);
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +0000844
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000845 if (!shaderObject)
846 {
daniel@transgaming.com0cefaf42010-04-13 03:26:36 +0000847 if (context->getProgram(shader))
848 {
849 return error(GL_INVALID_OPERATION);
850 }
851 else
852 {
853 return error(GL_INVALID_VALUE);
854 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000855 }
856
857 shaderObject->compile();
858 }
859 }
860 catch(std::bad_alloc&)
861 {
862 return error(GL_OUT_OF_MEMORY);
863 }
864}
865
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +0000866void __stdcall glCompressedTexImage2D(GLenum target, GLint level, GLenum internalformat, GLsizei width, GLsizei height,
867 GLint border, GLsizei imageSize, const GLvoid* data)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000868{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +0000869 EVENT("(GLenum target = 0x%X, GLint level = %d, GLenum internalformat = 0x%X, GLsizei width = %d, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +0000870 "GLsizei height = %d, GLint border = %d, GLsizei imageSize = %d, const GLvoid* data = 0x%0.8p)",
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000871 target, level, internalformat, width, height, border, imageSize, data);
872
873 try
874 {
daniel@transgaming.com4f9ef0d2011-05-30 23:51:19 +0000875 if (!validImageSize(level, width, height) || border != 0 || imageSize < 0)
daniel@transgaming.com41430492010-03-11 20:36:18 +0000876 {
877 return error(GL_INVALID_VALUE);
878 }
879
daniel@transgaming.com01868132010-08-24 19:21:17 +0000880 switch (internalformat)
881 {
882 case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
883 case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
gman@chromium.org50c526d2011-08-10 05:19:44 +0000884 case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
885 case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
daniel@transgaming.com01868132010-08-24 19:21:17 +0000886 break;
887 default:
888 return error(GL_INVALID_ENUM);
889 }
890
891 if (border != 0)
892 {
893 return error(GL_INVALID_VALUE);
894 }
895
daniel@transgaming.com9d788502011-11-09 17:46:55 +0000896 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com01868132010-08-24 19:21:17 +0000897
898 if (context)
899 {
daniel@transgaming.com5d752f22010-10-07 13:37:20 +0000900 if (level > context->getMaximumTextureLevel())
901 {
902 return error(GL_INVALID_VALUE);
903 }
904
905 switch (target)
906 {
907 case GL_TEXTURE_2D:
908 if (width > (context->getMaximumTextureDimension() >> level) ||
909 height > (context->getMaximumTextureDimension() >> level))
910 {
911 return error(GL_INVALID_VALUE);
912 }
913 break;
914 case GL_TEXTURE_CUBE_MAP_POSITIVE_X:
915 case GL_TEXTURE_CUBE_MAP_NEGATIVE_X:
916 case GL_TEXTURE_CUBE_MAP_POSITIVE_Y:
917 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y:
918 case GL_TEXTURE_CUBE_MAP_POSITIVE_Z:
919 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z:
920 if (width != height)
921 {
922 return error(GL_INVALID_VALUE);
923 }
924
925 if (width > (context->getMaximumCubeTextureDimension() >> level) ||
926 height > (context->getMaximumCubeTextureDimension() >> level))
927 {
928 return error(GL_INVALID_VALUE);
929 }
930 break;
931 default:
932 return error(GL_INVALID_ENUM);
933 }
934
gman@chromium.org50c526d2011-08-10 05:19:44 +0000935 switch (internalformat) {
936 case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
937 case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
938 if (!context->supportsDXT1Textures())
939 {
940 return error(GL_INVALID_ENUM); // in this case, it's as though the internal format switch failed
941 }
942 break;
943 case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
944 if (!context->supportsDXT3Textures())
945 {
946 return error(GL_INVALID_ENUM); // in this case, it's as though the internal format switch failed
947 }
948 break;
949 case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
950 if (!context->supportsDXT5Textures())
951 {
952 return error(GL_INVALID_ENUM); // in this case, it's as though the internal format switch failed
953 }
954 break;
955 default: UNREACHABLE();
daniel@transgaming.com01868132010-08-24 19:21:17 +0000956 }
957
958 if (imageSize != gl::ComputeCompressedSize(width, height, internalformat))
959 {
960 return error(GL_INVALID_VALUE);
961 }
962
963 if (target == GL_TEXTURE_2D)
964 {
965 gl::Texture2D *texture = context->getTexture2D();
966
967 if (!texture)
968 {
969 return error(GL_INVALID_OPERATION);
970 }
971
daniel@transgaming.com64a0fb22011-11-11 04:10:40 +0000972 if (texture->isImmutable())
973 {
974 return error(GL_INVALID_OPERATION);
975 }
976
daniel@transgaming.com01868132010-08-24 19:21:17 +0000977 texture->setCompressedImage(level, internalformat, width, height, imageSize, data);
978 }
979 else
980 {
981 gl::TextureCubeMap *texture = context->getTextureCubeMap();
982
983 if (!texture)
984 {
985 return error(GL_INVALID_OPERATION);
986 }
987
daniel@transgaming.com64a0fb22011-11-11 04:10:40 +0000988 if (texture->isImmutable())
989 {
990 return error(GL_INVALID_OPERATION);
991 }
992
daniel@transgaming.com01868132010-08-24 19:21:17 +0000993 switch (target)
994 {
995 case GL_TEXTURE_CUBE_MAP_POSITIVE_X:
996 case GL_TEXTURE_CUBE_MAP_NEGATIVE_X:
997 case GL_TEXTURE_CUBE_MAP_POSITIVE_Y:
998 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y:
999 case GL_TEXTURE_CUBE_MAP_POSITIVE_Z:
1000 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z:
1001 texture->setCompressedImage(target, level, internalformat, width, height, imageSize, data);
1002 break;
1003 default: UNREACHABLE();
1004 }
1005 }
1006 }
1007
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001008 }
1009 catch(std::bad_alloc&)
1010 {
1011 return error(GL_OUT_OF_MEMORY);
1012 }
1013}
1014
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00001015void __stdcall glCompressedTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
1016 GLenum format, GLsizei imageSize, const GLvoid* data)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001017{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001018 EVENT("(GLenum target = 0x%X, GLint level = %d, GLint xoffset = %d, GLint yoffset = %d, "
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001019 "GLsizei width = %d, GLsizei height = %d, GLenum format = 0x%X, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00001020 "GLsizei imageSize = %d, const GLvoid* data = 0x%0.8p)",
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001021 target, level, xoffset, yoffset, width, height, format, imageSize, data);
1022
1023 try
1024 {
apatrick@chromium.org551022e2012-01-23 19:56:54 +00001025 if (!gl::IsInternalTextureTarget(target))
daniel@transgaming.com41430492010-03-11 20:36:18 +00001026 {
1027 return error(GL_INVALID_ENUM);
1028 }
1029
daniel@transgaming.com4f9ef0d2011-05-30 23:51:19 +00001030 if (xoffset < 0 || yoffset < 0 || !validImageSize(level, width, height) || imageSize < 0)
daniel@transgaming.com41430492010-03-11 20:36:18 +00001031 {
1032 return error(GL_INVALID_VALUE);
1033 }
1034
daniel@transgaming.com01868132010-08-24 19:21:17 +00001035 switch (format)
daniel@transgaming.com41430492010-03-11 20:36:18 +00001036 {
daniel@transgaming.com01868132010-08-24 19:21:17 +00001037 case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
1038 case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
gman@chromium.org50c526d2011-08-10 05:19:44 +00001039 case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
1040 case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
daniel@transgaming.com01868132010-08-24 19:21:17 +00001041 break;
1042 default:
1043 return error(GL_INVALID_ENUM);
daniel@transgaming.com41430492010-03-11 20:36:18 +00001044 }
1045
daniel@transgaming.com01868132010-08-24 19:21:17 +00001046 if (width == 0 || height == 0 || data == NULL)
1047 {
1048 return;
1049 }
1050
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001051 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com01868132010-08-24 19:21:17 +00001052
1053 if (context)
1054 {
daniel@transgaming.com5d752f22010-10-07 13:37:20 +00001055 if (level > context->getMaximumTextureLevel())
1056 {
1057 return error(GL_INVALID_VALUE);
1058 }
1059
gman@chromium.org50c526d2011-08-10 05:19:44 +00001060 switch (format) {
1061 case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
1062 case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
1063 if (!context->supportsDXT1Textures())
1064 {
1065 return error(GL_INVALID_ENUM); // in this case, it's as though the internal format switch failed
1066 }
1067 break;
1068 case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
1069 if (!context->supportsDXT3Textures())
1070 {
1071 return error(GL_INVALID_ENUM); // in this case, it's as though the internal format switch failed
1072 }
1073 break;
1074 case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
1075 if (!context->supportsDXT5Textures())
1076 {
1077 return error(GL_INVALID_ENUM); // in this case, it's as though the internal format switch failed
1078 }
1079 break;
1080 default: UNREACHABLE();
daniel@transgaming.com01868132010-08-24 19:21:17 +00001081 }
1082
1083 if (imageSize != gl::ComputeCompressedSize(width, height, format))
1084 {
1085 return error(GL_INVALID_VALUE);
1086 }
1087
1088 if (xoffset % 4 != 0 || yoffset % 4 != 0)
1089 {
1090 return error(GL_INVALID_OPERATION); // we wait to check the offsets until this point, because the multiple-of-four restriction
gman@chromium.org50c526d2011-08-10 05:19:44 +00001091 // does not exist unless DXT textures are supported.
daniel@transgaming.com01868132010-08-24 19:21:17 +00001092 }
1093
1094 if (target == GL_TEXTURE_2D)
1095 {
1096 gl::Texture2D *texture = context->getTexture2D();
daniel@transgaming.com343373a2011-11-29 19:42:32 +00001097 if (validateSubImageParams(true, width, height, xoffset, yoffset, level, GL_NONE, texture))
daniel@transgaming.com01868132010-08-24 19:21:17 +00001098 {
daniel@transgaming.com343373a2011-11-29 19:42:32 +00001099 texture->subImageCompressed(level, xoffset, yoffset, width, height, format, imageSize, data);
daniel@transgaming.com01868132010-08-24 19:21:17 +00001100 }
daniel@transgaming.com01868132010-08-24 19:21:17 +00001101 }
1102 else if (gl::IsCubemapTextureTarget(target))
1103 {
1104 gl::TextureCubeMap *texture = context->getTextureCubeMap();
daniel@transgaming.com343373a2011-11-29 19:42:32 +00001105 if (validateSubImageParams(true, width, height, xoffset, yoffset, level, GL_NONE, texture))
daniel@transgaming.com01868132010-08-24 19:21:17 +00001106 {
daniel@transgaming.com343373a2011-11-29 19:42:32 +00001107 texture->subImageCompressed(target, level, xoffset, yoffset, width, height, format, imageSize, data);
daniel@transgaming.com01868132010-08-24 19:21:17 +00001108 }
daniel@transgaming.com01868132010-08-24 19:21:17 +00001109 }
1110 else
1111 {
1112 UNREACHABLE();
1113 }
1114 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001115 }
1116 catch(std::bad_alloc&)
1117 {
1118 return error(GL_OUT_OF_MEMORY);
1119 }
1120}
1121
1122void __stdcall glCopyTexImage2D(GLenum target, GLint level, GLenum internalformat, GLint x, GLint y, GLsizei width, GLsizei height, GLint border)
1123{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001124 EVENT("(GLenum target = 0x%X, GLint level = %d, GLenum internalformat = 0x%X, "
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001125 "GLint x = %d, GLint y = %d, GLsizei width = %d, GLsizei height = %d, GLint border = %d)",
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001126 target, level, internalformat, x, y, width, height, border);
1127
1128 try
1129 {
daniel@transgaming.com4f9ef0d2011-05-30 23:51:19 +00001130 if (!validImageSize(level, width, height))
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001131 {
1132 return error(GL_INVALID_VALUE);
1133 }
1134
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001135 if (border != 0)
1136 {
1137 return error(GL_INVALID_VALUE);
1138 }
1139
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001140 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001141
1142 if (context)
1143 {
daniel@transgaming.com32b11442011-11-19 02:42:48 +00001144 if (level > context->getMaximumTextureLevel())
1145 {
1146 return error(GL_INVALID_VALUE);
1147 }
1148
daniel@transgaming.com5d752f22010-10-07 13:37:20 +00001149 switch (target)
1150 {
1151 case GL_TEXTURE_2D:
1152 if (width > (context->getMaximumTextureDimension() >> level) ||
1153 height > (context->getMaximumTextureDimension() >> level))
1154 {
1155 return error(GL_INVALID_VALUE);
1156 }
1157 break;
1158 case GL_TEXTURE_CUBE_MAP_POSITIVE_X:
1159 case GL_TEXTURE_CUBE_MAP_NEGATIVE_X:
1160 case GL_TEXTURE_CUBE_MAP_POSITIVE_Y:
1161 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y:
1162 case GL_TEXTURE_CUBE_MAP_POSITIVE_Z:
1163 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z:
1164 if (width != height)
1165 {
1166 return error(GL_INVALID_VALUE);
1167 }
1168
1169 if (width > (context->getMaximumCubeTextureDimension() >> level) ||
1170 height > (context->getMaximumCubeTextureDimension() >> level))
1171 {
1172 return error(GL_INVALID_VALUE);
1173 }
1174 break;
1175 default:
1176 return error(GL_INVALID_ENUM);
1177 }
1178
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +00001179 gl::Framebuffer *framebuffer = context->getReadFramebuffer();
daniel@transgaming.com3f85fbb2010-10-15 17:58:05 +00001180
daniel@transgaming.combbc57792010-07-28 19:21:05 +00001181 if (framebuffer->completeness() != GL_FRAMEBUFFER_COMPLETE)
1182 {
1183 return error(GL_INVALID_FRAMEBUFFER_OPERATION);
1184 }
1185
daniel@transgaming.com1f135d82010-08-24 19:20:36 +00001186 if (context->getReadFramebufferHandle() != 0 && framebuffer->getColorbuffer()->getSamples() != 0)
1187 {
1188 return error(GL_INVALID_OPERATION);
1189 }
1190
daniel@transgaming.comd14558a2011-11-09 17:46:18 +00001191 gl::Renderbuffer *source = framebuffer->getColorbuffer();
daniel@transgaming.comd2fd4f22011-02-01 18:49:11 +00001192 GLenum colorbufferFormat = source->getInternalFormat();
daniel@transgaming.com3f85fbb2010-10-15 17:58:05 +00001193
1194 // [OpenGL ES 2.0.24] table 3.9
1195 switch (internalformat)
1196 {
1197 case GL_ALPHA:
1198 if (colorbufferFormat != GL_ALPHA &&
1199 colorbufferFormat != GL_RGBA &&
1200 colorbufferFormat != GL_RGBA4 &&
1201 colorbufferFormat != GL_RGB5_A1 &&
1202 colorbufferFormat != GL_RGBA8_OES)
1203 {
1204 return error(GL_INVALID_OPERATION);
1205 }
1206 break;
1207 case GL_LUMINANCE:
1208 case GL_RGB:
1209 if (colorbufferFormat != GL_RGB &&
1210 colorbufferFormat != GL_RGB565 &&
1211 colorbufferFormat != GL_RGB8_OES &&
1212 colorbufferFormat != GL_RGBA &&
1213 colorbufferFormat != GL_RGBA4 &&
1214 colorbufferFormat != GL_RGB5_A1 &&
1215 colorbufferFormat != GL_RGBA8_OES)
1216 {
1217 return error(GL_INVALID_OPERATION);
1218 }
1219 break;
1220 case GL_LUMINANCE_ALPHA:
1221 case GL_RGBA:
1222 if (colorbufferFormat != GL_RGBA &&
1223 colorbufferFormat != GL_RGBA4 &&
1224 colorbufferFormat != GL_RGB5_A1 &&
1225 colorbufferFormat != GL_RGBA8_OES)
1226 {
1227 return error(GL_INVALID_OPERATION);
1228 }
1229 break;
1230 case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
1231 case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
gman@chromium.org50c526d2011-08-10 05:19:44 +00001232 if (context->supportsDXT1Textures())
1233 {
1234 return error(GL_INVALID_OPERATION);
1235 }
1236 else
1237 {
1238 return error(GL_INVALID_ENUM);
1239 }
1240 break;
1241 case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
1242 if (context->supportsDXT3Textures())
1243 {
1244 return error(GL_INVALID_OPERATION);
1245 }
1246 else
1247 {
1248 return error(GL_INVALID_ENUM);
1249 }
1250 break;
1251 case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
1252 if (context->supportsDXT5Textures())
daniel@transgaming.com3f85fbb2010-10-15 17:58:05 +00001253 {
1254 return error(GL_INVALID_OPERATION);
1255 }
1256 else
1257 {
1258 return error(GL_INVALID_ENUM);
1259 }
1260 break;
1261 default:
1262 return error(GL_INVALID_ENUM);
1263 }
1264
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001265 if (target == GL_TEXTURE_2D)
1266 {
1267 gl::Texture2D *texture = context->getTexture2D();
1268
1269 if (!texture)
1270 {
1271 return error(GL_INVALID_OPERATION);
1272 }
daniel@transgaming.com0a337e92010-08-28 17:38:27 +00001273
daniel@transgaming.com64a0fb22011-11-11 04:10:40 +00001274 if (texture->isImmutable())
1275 {
1276 return error(GL_INVALID_OPERATION);
1277 }
1278
apatrick@chromium.orgb31f5322011-01-19 19:02:52 +00001279 texture->copyImage(level, internalformat, x, y, width, height, framebuffer);
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001280 }
daniel@transgaming.com19ffc242010-05-04 03:35:21 +00001281 else if (gl::IsCubemapTextureTarget(target))
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001282 {
1283 gl::TextureCubeMap *texture = context->getTextureCubeMap();
1284
1285 if (!texture)
1286 {
1287 return error(GL_INVALID_OPERATION);
1288 }
1289
daniel@transgaming.com64a0fb22011-11-11 04:10:40 +00001290 if (texture->isImmutable())
1291 {
1292 return error(GL_INVALID_OPERATION);
1293 }
1294
apatrick@chromium.orgb31f5322011-01-19 19:02:52 +00001295 texture->copyImage(target, level, internalformat, x, y, width, height, framebuffer);
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001296 }
daniel@transgaming.com3f85fbb2010-10-15 17:58:05 +00001297 else UNREACHABLE();
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001298 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001299 }
1300 catch(std::bad_alloc&)
1301 {
1302 return error(GL_OUT_OF_MEMORY);
1303 }
1304}
1305
1306void __stdcall glCopyTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height)
1307{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001308 EVENT("(GLenum target = 0x%X, GLint level = %d, GLint xoffset = %d, GLint yoffset = %d, "
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001309 "GLint x = %d, GLint y = %d, GLsizei width = %d, GLsizei height = %d)",
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001310 target, level, xoffset, yoffset, x, y, width, height);
1311
1312 try
1313 {
apatrick@chromium.org551022e2012-01-23 19:56:54 +00001314 if (!gl::IsInternalTextureTarget(target))
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001315 {
1316 return error(GL_INVALID_ENUM);
1317 }
1318
daniel@transgaming.com5d752f22010-10-07 13:37:20 +00001319 if (level < 0 || xoffset < 0 || yoffset < 0 || width < 0 || height < 0)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001320 {
1321 return error(GL_INVALID_VALUE);
1322 }
1323
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001324 if (std::numeric_limits<GLsizei>::max() - xoffset < width || std::numeric_limits<GLsizei>::max() - yoffset < height)
1325 {
1326 return error(GL_INVALID_VALUE);
1327 }
1328
1329 if (width == 0 || height == 0)
1330 {
1331 return;
1332 }
1333
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001334 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001335
1336 if (context)
1337 {
daniel@transgaming.com5d752f22010-10-07 13:37:20 +00001338 if (level > context->getMaximumTextureLevel())
1339 {
1340 return error(GL_INVALID_VALUE);
1341 }
1342
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +00001343 gl::Framebuffer *framebuffer = context->getReadFramebuffer();
daniel@transgaming.com3f85fbb2010-10-15 17:58:05 +00001344
daniel@transgaming.combbc57792010-07-28 19:21:05 +00001345 if (framebuffer->completeness() != GL_FRAMEBUFFER_COMPLETE)
1346 {
1347 return error(GL_INVALID_FRAMEBUFFER_OPERATION);
1348 }
1349
daniel@transgaming.com1f135d82010-08-24 19:20:36 +00001350 if (context->getReadFramebufferHandle() != 0 && framebuffer->getColorbuffer()->getSamples() != 0)
1351 {
1352 return error(GL_INVALID_OPERATION);
1353 }
1354
daniel@transgaming.comd14558a2011-11-09 17:46:18 +00001355 gl::Renderbuffer *source = framebuffer->getColorbuffer();
daniel@transgaming.comd2fd4f22011-02-01 18:49:11 +00001356 GLenum colorbufferFormat = source->getInternalFormat();
daniel@transgaming.com3f85fbb2010-10-15 17:58:05 +00001357 gl::Texture *texture = NULL;
1358
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001359 if (target == GL_TEXTURE_2D)
1360 {
daniel@transgaming.com3f85fbb2010-10-15 17:58:05 +00001361 texture = context->getTexture2D();
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001362 }
daniel@transgaming.com19ffc242010-05-04 03:35:21 +00001363 else if (gl::IsCubemapTextureTarget(target))
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001364 {
daniel@transgaming.com3f85fbb2010-10-15 17:58:05 +00001365 texture = context->getTextureCubeMap();
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001366 }
daniel@transgaming.com3f85fbb2010-10-15 17:58:05 +00001367 else UNREACHABLE();
1368
daniel@transgaming.com343373a2011-11-29 19:42:32 +00001369 if (!validateSubImageParams(false, width, height, xoffset, yoffset, level, GL_NONE, texture))
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001370 {
daniel@transgaming.com343373a2011-11-29 19:42:32 +00001371 return; // error already registered by validateSubImageParams
daniel@transgaming.com21f05d72011-11-29 19:42:28 +00001372 }
1373
daniel@transgaming.comd2fd4f22011-02-01 18:49:11 +00001374 GLenum textureFormat = texture->getInternalFormat();
daniel@transgaming.com3f85fbb2010-10-15 17:58:05 +00001375
1376 // [OpenGL ES 2.0.24] table 3.9
1377 switch (textureFormat)
1378 {
1379 case GL_ALPHA:
1380 if (colorbufferFormat != GL_ALPHA &&
1381 colorbufferFormat != GL_RGBA &&
1382 colorbufferFormat != GL_RGBA4 &&
1383 colorbufferFormat != GL_RGB5_A1 &&
1384 colorbufferFormat != GL_RGBA8_OES)
1385 {
1386 return error(GL_INVALID_OPERATION);
1387 }
1388 break;
1389 case GL_LUMINANCE:
1390 case GL_RGB:
1391 if (colorbufferFormat != GL_RGB &&
1392 colorbufferFormat != GL_RGB565 &&
1393 colorbufferFormat != GL_RGB8_OES &&
1394 colorbufferFormat != GL_RGBA &&
1395 colorbufferFormat != GL_RGBA4 &&
1396 colorbufferFormat != GL_RGB5_A1 &&
1397 colorbufferFormat != GL_RGBA8_OES)
1398 {
1399 return error(GL_INVALID_OPERATION);
1400 }
1401 break;
1402 case GL_LUMINANCE_ALPHA:
1403 case GL_RGBA:
1404 if (colorbufferFormat != GL_RGBA &&
1405 colorbufferFormat != GL_RGBA4 &&
1406 colorbufferFormat != GL_RGB5_A1 &&
1407 colorbufferFormat != GL_RGBA8_OES)
1408 {
1409 return error(GL_INVALID_OPERATION);
1410 }
1411 break;
1412 case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
1413 case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
gman@chromium.org50c526d2011-08-10 05:19:44 +00001414 case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
1415 case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
daniel@transgaming.com3f85fbb2010-10-15 17:58:05 +00001416 return error(GL_INVALID_OPERATION);
1417 default:
1418 return error(GL_INVALID_OPERATION);
1419 }
1420
apatrick@chromium.orgb31f5322011-01-19 19:02:52 +00001421 texture->copySubImage(target, level, xoffset, yoffset, x, y, width, height, framebuffer);
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001422 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001423 }
daniel@transgaming.comb8c28ed2010-04-13 03:26:32 +00001424
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001425 catch(std::bad_alloc&)
1426 {
1427 return error(GL_OUT_OF_MEMORY);
1428 }
1429}
1430
1431GLuint __stdcall glCreateProgram(void)
1432{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001433 EVENT("()");
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001434
1435 try
1436 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001437 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001438
1439 if (context)
1440 {
1441 return context->createProgram();
1442 }
1443 }
1444 catch(std::bad_alloc&)
1445 {
1446 return error(GL_OUT_OF_MEMORY, 0);
1447 }
1448
1449 return 0;
1450}
1451
1452GLuint __stdcall glCreateShader(GLenum type)
1453{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001454 EVENT("(GLenum type = 0x%X)", type);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001455
1456 try
1457 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001458 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001459
1460 if (context)
1461 {
1462 switch (type)
1463 {
1464 case GL_FRAGMENT_SHADER:
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00001465 case GL_VERTEX_SHADER:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001466 return context->createShader(type);
1467 default:
1468 return error(GL_INVALID_ENUM, 0);
1469 }
1470 }
1471 }
1472 catch(std::bad_alloc&)
1473 {
1474 return error(GL_OUT_OF_MEMORY, 0);
1475 }
1476
1477 return 0;
1478}
1479
1480void __stdcall glCullFace(GLenum mode)
1481{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001482 EVENT("(GLenum mode = 0x%X)", mode);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001483
1484 try
1485 {
1486 switch (mode)
1487 {
1488 case GL_FRONT:
1489 case GL_BACK:
1490 case GL_FRONT_AND_BACK:
1491 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001492 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001493
1494 if (context)
1495 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00001496 context->setCullMode(mode);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001497 }
1498 }
1499 break;
1500 default:
1501 return error(GL_INVALID_ENUM);
1502 }
1503 }
1504 catch(std::bad_alloc&)
1505 {
1506 return error(GL_OUT_OF_MEMORY);
1507 }
1508}
1509
1510void __stdcall glDeleteBuffers(GLsizei n, const GLuint* buffers)
1511{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001512 EVENT("(GLsizei n = %d, const GLuint* buffers = 0x%0.8p)", n, buffers);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001513
1514 try
1515 {
1516 if (n < 0)
1517 {
1518 return error(GL_INVALID_VALUE);
1519 }
1520
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001521 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001522
1523 if (context)
1524 {
1525 for (int i = 0; i < n; i++)
1526 {
1527 context->deleteBuffer(buffers[i]);
1528 }
1529 }
1530 }
1531 catch(std::bad_alloc&)
1532 {
1533 return error(GL_OUT_OF_MEMORY);
1534 }
1535}
1536
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00001537void __stdcall glDeleteFencesNV(GLsizei n, const GLuint* fences)
1538{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001539 EVENT("(GLsizei n = %d, const GLuint* fences = 0x%0.8p)", n, fences);
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00001540
1541 try
1542 {
1543 if (n < 0)
1544 {
1545 return error(GL_INVALID_VALUE);
1546 }
1547
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001548 gl::Context *context = gl::getNonLostContext();
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00001549
1550 if (context)
1551 {
1552 for (int i = 0; i < n; i++)
1553 {
1554 context->deleteFence(fences[i]);
1555 }
1556 }
1557 }
1558 catch(std::bad_alloc&)
1559 {
1560 return error(GL_OUT_OF_MEMORY);
1561 }
1562}
1563
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001564void __stdcall glDeleteFramebuffers(GLsizei n, const GLuint* framebuffers)
1565{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001566 EVENT("(GLsizei n = %d, const GLuint* framebuffers = 0x%0.8p)", n, framebuffers);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001567
1568 try
1569 {
1570 if (n < 0)
1571 {
1572 return error(GL_INVALID_VALUE);
1573 }
1574
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001575 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001576
1577 if (context)
1578 {
1579 for (int i = 0; i < n; i++)
1580 {
1581 if (framebuffers[i] != 0)
1582 {
1583 context->deleteFramebuffer(framebuffers[i]);
1584 }
1585 }
1586 }
1587 }
1588 catch(std::bad_alloc&)
1589 {
1590 return error(GL_OUT_OF_MEMORY);
1591 }
1592}
1593
1594void __stdcall glDeleteProgram(GLuint program)
1595{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001596 EVENT("(GLuint program = %d)", program);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001597
1598 try
1599 {
daniel@transgaming.com75401e62010-04-13 03:26:39 +00001600 if (program == 0)
1601 {
1602 return;
1603 }
1604
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001605 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001606
1607 if (context)
1608 {
daniel@transgaming.com75401e62010-04-13 03:26:39 +00001609 if (!context->getProgram(program))
1610 {
1611 if(context->getShader(program))
1612 {
1613 return error(GL_INVALID_OPERATION);
1614 }
1615 else
1616 {
1617 return error(GL_INVALID_VALUE);
1618 }
1619 }
1620
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001621 context->deleteProgram(program);
1622 }
1623 }
1624 catch(std::bad_alloc&)
1625 {
1626 return error(GL_OUT_OF_MEMORY);
1627 }
1628}
1629
daniel@transgaming.com86bdb822012-01-20 18:24:39 +00001630void __stdcall glDeleteQueriesEXT(GLsizei n, const GLuint *ids)
1631{
1632 EVENT("(GLsizei n = %d, const GLuint *ids = 0x%0.8p)", n, ids);
1633
1634 try
1635 {
1636 if (n < 0)
1637 {
1638 return error(GL_INVALID_VALUE);
1639 }
1640
1641 gl::Context *context = gl::getNonLostContext();
1642
1643 if (context)
1644 {
1645 for (int i = 0; i < n; i++)
1646 {
1647 context->deleteQuery(ids[i]);
1648 }
1649 }
1650 }
1651 catch(std::bad_alloc&)
1652 {
1653 return error(GL_OUT_OF_MEMORY);
1654 }
1655}
1656
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001657void __stdcall glDeleteRenderbuffers(GLsizei n, const GLuint* renderbuffers)
1658{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001659 EVENT("(GLsizei n = %d, const GLuint* renderbuffers = 0x%0.8p)", n, renderbuffers);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001660
1661 try
1662 {
1663 if (n < 0)
1664 {
1665 return error(GL_INVALID_VALUE);
1666 }
1667
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001668 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001669
1670 if (context)
1671 {
daniel@transgaming.come2b22122010-03-11 19:22:14 +00001672 for (int i = 0; i < n; i++)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001673 {
1674 context->deleteRenderbuffer(renderbuffers[i]);
1675 }
1676 }
1677 }
1678 catch(std::bad_alloc&)
1679 {
1680 return error(GL_OUT_OF_MEMORY);
1681 }
1682}
1683
1684void __stdcall glDeleteShader(GLuint shader)
1685{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001686 EVENT("(GLuint shader = %d)", shader);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001687
1688 try
1689 {
daniel@transgaming.com75401e62010-04-13 03:26:39 +00001690 if (shader == 0)
1691 {
1692 return;
1693 }
1694
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001695 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001696
1697 if (context)
1698 {
daniel@transgaming.com75401e62010-04-13 03:26:39 +00001699 if (!context->getShader(shader))
1700 {
1701 if(context->getProgram(shader))
1702 {
1703 return error(GL_INVALID_OPERATION);
1704 }
1705 else
1706 {
1707 return error(GL_INVALID_VALUE);
1708 }
1709 }
1710
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001711 context->deleteShader(shader);
1712 }
1713 }
1714 catch(std::bad_alloc&)
1715 {
1716 return error(GL_OUT_OF_MEMORY);
1717 }
1718}
1719
1720void __stdcall glDeleteTextures(GLsizei n, const GLuint* textures)
1721{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001722 EVENT("(GLsizei n = %d, const GLuint* textures = 0x%0.8p)", n, textures);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001723
1724 try
1725 {
1726 if (n < 0)
1727 {
1728 return error(GL_INVALID_VALUE);
1729 }
1730
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001731 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001732
1733 if (context)
1734 {
1735 for (int i = 0; i < n; i++)
1736 {
1737 if (textures[i] != 0)
1738 {
1739 context->deleteTexture(textures[i]);
1740 }
1741 }
1742 }
1743 }
1744 catch(std::bad_alloc&)
1745 {
1746 return error(GL_OUT_OF_MEMORY);
1747 }
1748}
1749
1750void __stdcall glDepthFunc(GLenum func)
1751{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001752 EVENT("(GLenum func = 0x%X)", func);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001753
1754 try
1755 {
1756 switch (func)
1757 {
1758 case GL_NEVER:
1759 case GL_ALWAYS:
1760 case GL_LESS:
1761 case GL_LEQUAL:
1762 case GL_EQUAL:
1763 case GL_GREATER:
1764 case GL_GEQUAL:
1765 case GL_NOTEQUAL:
1766 break;
1767 default:
1768 return error(GL_INVALID_ENUM);
1769 }
1770
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001771 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001772
1773 if (context)
1774 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00001775 context->setDepthFunc(func);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001776 }
1777 }
1778 catch(std::bad_alloc&)
1779 {
1780 return error(GL_OUT_OF_MEMORY);
1781 }
1782}
1783
1784void __stdcall glDepthMask(GLboolean flag)
1785{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001786 EVENT("(GLboolean flag = %d)", flag);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001787
1788 try
1789 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001790 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001791
1792 if (context)
1793 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00001794 context->setDepthMask(flag != GL_FALSE);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001795 }
1796 }
1797 catch(std::bad_alloc&)
1798 {
1799 return error(GL_OUT_OF_MEMORY);
1800 }
1801}
1802
1803void __stdcall glDepthRangef(GLclampf zNear, GLclampf zFar)
1804{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001805 EVENT("(GLclampf zNear = %f, GLclampf zFar = %f)", zNear, zFar);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001806
1807 try
1808 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001809 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001810
1811 if (context)
1812 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00001813 context->setDepthRange(zNear, zFar);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001814 }
1815 }
1816 catch(std::bad_alloc&)
1817 {
1818 return error(GL_OUT_OF_MEMORY);
1819 }
1820}
1821
1822void __stdcall glDetachShader(GLuint program, GLuint shader)
1823{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001824 EVENT("(GLuint program = %d, GLuint shader = %d)", program, shader);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001825
1826 try
1827 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001828 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001829
1830 if (context)
1831 {
daniel@transgaming.com73c2c2e2010-04-13 03:26:11 +00001832
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001833 gl::Program *programObject = context->getProgram(program);
1834 gl::Shader *shaderObject = context->getShader(shader);
daniel@transgaming.com73c2c2e2010-04-13 03:26:11 +00001835
1836 if (!programObject)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001837 {
daniel@transgaming.com73c2c2e2010-04-13 03:26:11 +00001838 gl::Shader *shaderByProgramHandle;
1839 shaderByProgramHandle = context->getShader(program);
1840 if (!shaderByProgramHandle)
1841 {
1842 return error(GL_INVALID_VALUE);
1843 }
1844 else
1845 {
1846 return error(GL_INVALID_OPERATION);
1847 }
1848 }
1849
1850 if (!shaderObject)
1851 {
1852 gl::Program *programByShaderHandle = context->getProgram(shader);
1853 if (!programByShaderHandle)
1854 {
1855 return error(GL_INVALID_VALUE);
1856 }
1857 else
1858 {
1859 return error(GL_INVALID_OPERATION);
1860 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001861 }
1862
1863 if (!programObject->detachShader(shaderObject))
1864 {
1865 return error(GL_INVALID_OPERATION);
1866 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001867 }
1868 }
1869 catch(std::bad_alloc&)
1870 {
1871 return error(GL_OUT_OF_MEMORY);
1872 }
1873}
1874
1875void __stdcall glDisable(GLenum cap)
1876{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001877 EVENT("(GLenum cap = 0x%X)", cap);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001878
1879 try
1880 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001881 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001882
1883 if (context)
1884 {
1885 switch (cap)
1886 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00001887 case GL_CULL_FACE: context->setCullFace(false); break;
1888 case GL_POLYGON_OFFSET_FILL: context->setPolygonOffsetFill(false); break;
1889 case GL_SAMPLE_ALPHA_TO_COVERAGE: context->setSampleAlphaToCoverage(false); break;
1890 case GL_SAMPLE_COVERAGE: context->setSampleCoverage(false); break;
1891 case GL_SCISSOR_TEST: context->setScissorTest(false); break;
1892 case GL_STENCIL_TEST: context->setStencilTest(false); break;
1893 case GL_DEPTH_TEST: context->setDepthTest(false); break;
1894 case GL_BLEND: context->setBlend(false); break;
1895 case GL_DITHER: context->setDither(false); break;
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001896 default:
1897 return error(GL_INVALID_ENUM);
1898 }
1899 }
1900 }
1901 catch(std::bad_alloc&)
1902 {
1903 return error(GL_OUT_OF_MEMORY);
1904 }
1905}
1906
1907void __stdcall glDisableVertexAttribArray(GLuint index)
1908{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001909 EVENT("(GLuint index = %d)", index);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001910
1911 try
1912 {
1913 if (index >= gl::MAX_VERTEX_ATTRIBS)
1914 {
1915 return error(GL_INVALID_VALUE);
1916 }
1917
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001918 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001919
1920 if (context)
1921 {
daniel@transgaming.com83921382011-01-08 05:46:00 +00001922 context->setEnableVertexAttribArray(index, false);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001923 }
1924 }
1925 catch(std::bad_alloc&)
1926 {
1927 return error(GL_OUT_OF_MEMORY);
1928 }
1929}
1930
1931void __stdcall glDrawArrays(GLenum mode, GLint first, GLsizei count)
1932{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001933 EVENT("(GLenum mode = 0x%X, GLint first = %d, GLsizei count = %d)", mode, first, count);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001934
1935 try
1936 {
1937 if (count < 0 || first < 0)
1938 {
1939 return error(GL_INVALID_VALUE);
1940 }
1941
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001942 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001943
1944 if (context)
1945 {
daniel@transgaming.com8ca9c6e2012-01-27 15:38:54 +00001946 context->drawArrays(mode, first, count, 0);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001947 }
1948 }
1949 catch(std::bad_alloc&)
1950 {
1951 return error(GL_OUT_OF_MEMORY);
1952 }
1953}
1954
daniel@transgaming.comd2820bf2012-01-27 15:38:48 +00001955void __stdcall glDrawArraysInstancedANGLE(GLenum mode, GLint first, GLsizei count, GLsizei primcount)
1956{
1957 EVENT("(GLenum mode = 0x%X, GLint first = %d, GLsizei count = %d, GLsizei primcount = %d)", mode, first, count, primcount);
1958
1959 try
1960 {
1961 if (count < 0 || first < 0 || primcount < 0)
1962 {
1963 return error(GL_INVALID_VALUE);
1964 }
1965
daniel@transgaming.com8ca9c6e2012-01-27 15:38:54 +00001966 if (primcount > 0)
daniel@transgaming.comd2820bf2012-01-27 15:38:48 +00001967 {
daniel@transgaming.com8ca9c6e2012-01-27 15:38:54 +00001968 gl::Context *context = gl::getNonLostContext();
1969
1970 if (context)
1971 {
1972 context->drawArrays(mode, first, count, primcount);
1973 }
daniel@transgaming.comd2820bf2012-01-27 15:38:48 +00001974 }
1975 }
1976 catch(std::bad_alloc&)
1977 {
1978 return error(GL_OUT_OF_MEMORY);
1979 }
1980}
1981
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00001982void __stdcall glDrawElements(GLenum mode, GLsizei count, GLenum type, const GLvoid* indices)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001983{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00001984 EVENT("(GLenum mode = 0x%X, GLsizei count = %d, GLenum type = 0x%X, const GLvoid* indices = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001985 mode, count, type, indices);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001986
1987 try
1988 {
1989 if (count < 0)
1990 {
1991 return error(GL_INVALID_VALUE);
1992 }
1993
daniel@transgaming.com9d788502011-11-09 17:46:55 +00001994 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001995
1996 if (context)
1997 {
daniel@transgaming.com83921382011-01-08 05:46:00 +00001998 switch (type)
1999 {
2000 case GL_UNSIGNED_BYTE:
2001 case GL_UNSIGNED_SHORT:
2002 break;
2003 case GL_UNSIGNED_INT:
2004 if (!context->supports32bitIndices())
2005 {
2006 return error(GL_INVALID_ENUM);
2007 }
2008 break;
2009 default:
2010 return error(GL_INVALID_ENUM);
2011 }
2012
daniel@transgaming.com8ca9c6e2012-01-27 15:38:54 +00002013 context->drawElements(mode, count, type, indices, 0);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002014 }
2015 }
2016 catch(std::bad_alloc&)
2017 {
2018 return error(GL_OUT_OF_MEMORY);
2019 }
2020}
2021
daniel@transgaming.comd2820bf2012-01-27 15:38:48 +00002022void __stdcall glDrawElementsInstancedANGLE(GLenum mode, GLsizei count, GLenum type, const GLvoid *indices, GLsizei primcount)
2023{
2024 EVENT("(GLenum mode = 0x%X, GLsizei count = %d, GLenum type = 0x%X, const GLvoid* indices = 0x%0.8p, GLsizei primcount = %d)",
2025 mode, count, type, indices, primcount);
2026
2027 try
2028 {
2029 if (count < 0 || primcount < 0)
2030 {
2031 return error(GL_INVALID_VALUE);
2032 }
2033
daniel@transgaming.com8ca9c6e2012-01-27 15:38:54 +00002034 if (primcount > 0)
daniel@transgaming.comd2820bf2012-01-27 15:38:48 +00002035 {
daniel@transgaming.com8ca9c6e2012-01-27 15:38:54 +00002036 gl::Context *context = gl::getNonLostContext();
2037
2038 if (context)
daniel@transgaming.comd2820bf2012-01-27 15:38:48 +00002039 {
daniel@transgaming.com8ca9c6e2012-01-27 15:38:54 +00002040 switch (type)
daniel@transgaming.comd2820bf2012-01-27 15:38:48 +00002041 {
daniel@transgaming.com8ca9c6e2012-01-27 15:38:54 +00002042 case GL_UNSIGNED_BYTE:
2043 case GL_UNSIGNED_SHORT:
2044 break;
2045 case GL_UNSIGNED_INT:
2046 if (!context->supports32bitIndices())
2047 {
2048 return error(GL_INVALID_ENUM);
2049 }
2050 break;
2051 default:
2052 return error(GL_INVALID_ENUM);
daniel@transgaming.comd2820bf2012-01-27 15:38:48 +00002053 }
daniel@transgaming.com8ca9c6e2012-01-27 15:38:54 +00002054
2055 context->drawElements(mode, count, type, indices, primcount);
daniel@transgaming.comd2820bf2012-01-27 15:38:48 +00002056 }
daniel@transgaming.comd2820bf2012-01-27 15:38:48 +00002057 }
2058 }
2059 catch(std::bad_alloc&)
2060 {
2061 return error(GL_OUT_OF_MEMORY);
2062 }
2063}
2064
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002065void __stdcall glEnable(GLenum cap)
2066{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002067 EVENT("(GLenum cap = 0x%X)", cap);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002068
2069 try
2070 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002071 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002072
2073 if (context)
2074 {
2075 switch (cap)
2076 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00002077 case GL_CULL_FACE: context->setCullFace(true); break;
2078 case GL_POLYGON_OFFSET_FILL: context->setPolygonOffsetFill(true); break;
2079 case GL_SAMPLE_ALPHA_TO_COVERAGE: context->setSampleAlphaToCoverage(true); break;
2080 case GL_SAMPLE_COVERAGE: context->setSampleCoverage(true); break;
2081 case GL_SCISSOR_TEST: context->setScissorTest(true); break;
2082 case GL_STENCIL_TEST: context->setStencilTest(true); break;
2083 case GL_DEPTH_TEST: context->setDepthTest(true); break;
2084 case GL_BLEND: context->setBlend(true); break;
2085 case GL_DITHER: context->setDither(true); break;
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002086 default:
2087 return error(GL_INVALID_ENUM);
2088 }
2089 }
2090 }
2091 catch(std::bad_alloc&)
2092 {
2093 return error(GL_OUT_OF_MEMORY);
2094 }
2095}
2096
2097void __stdcall glEnableVertexAttribArray(GLuint index)
2098{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002099 EVENT("(GLuint index = %d)", index);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002100
2101 try
2102 {
2103 if (index >= gl::MAX_VERTEX_ATTRIBS)
2104 {
2105 return error(GL_INVALID_VALUE);
2106 }
2107
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002108 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002109
2110 if (context)
2111 {
daniel@transgaming.com83921382011-01-08 05:46:00 +00002112 context->setEnableVertexAttribArray(index, true);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002113 }
2114 }
2115 catch(std::bad_alloc&)
2116 {
2117 return error(GL_OUT_OF_MEMORY);
2118 }
2119}
2120
daniel@transgaming.com86bdb822012-01-20 18:24:39 +00002121void __stdcall glEndQueryEXT(GLenum target)
2122{
2123 EVENT("GLenum target = 0x%X)", target);
2124
2125 try
2126 {
2127 switch (target)
2128 {
2129 case GL_ANY_SAMPLES_PASSED_EXT:
2130 case GL_ANY_SAMPLES_PASSED_CONSERVATIVE_EXT:
2131 break;
2132 default:
2133 return error(GL_INVALID_ENUM);
2134 }
2135
2136 gl::Context *context = gl::getNonLostContext();
2137
2138 if (context)
2139 {
2140 context->endQuery(target);
2141 }
2142 }
2143 catch(std::bad_alloc&)
2144 {
2145 return error(GL_OUT_OF_MEMORY);
2146 }
2147}
2148
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00002149void __stdcall glFinishFenceNV(GLuint fence)
2150{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002151 EVENT("(GLuint fence = %d)", fence);
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00002152
2153 try
2154 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002155 gl::Context *context = gl::getNonLostContext();
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00002156
2157 if (context)
2158 {
2159 gl::Fence* fenceObject = context->getFence(fence);
2160
2161 if (fenceObject == NULL)
2162 {
2163 return error(GL_INVALID_OPERATION);
2164 }
2165
2166 fenceObject->finishFence();
2167 }
2168 }
2169 catch(std::bad_alloc&)
2170 {
2171 return error(GL_OUT_OF_MEMORY);
2172 }
2173}
2174
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002175void __stdcall glFinish(void)
2176{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002177 EVENT("()");
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002178
2179 try
2180 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002181 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002182
2183 if (context)
2184 {
daniel@transgaming.com0d86aa72011-10-26 02:35:10 +00002185 context->sync(true);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002186 }
2187 }
2188 catch(std::bad_alloc&)
2189 {
2190 return error(GL_OUT_OF_MEMORY);
2191 }
2192}
2193
2194void __stdcall glFlush(void)
2195{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002196 EVENT("()");
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002197
2198 try
2199 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002200 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002201
2202 if (context)
2203 {
daniel@transgaming.com0d86aa72011-10-26 02:35:10 +00002204 context->sync(false);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002205 }
2206 }
2207 catch(std::bad_alloc&)
2208 {
2209 return error(GL_OUT_OF_MEMORY);
2210 }
2211}
2212
2213void __stdcall glFramebufferRenderbuffer(GLenum target, GLenum attachment, GLenum renderbuffertarget, GLuint renderbuffer)
2214{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002215 EVENT("(GLenum target = 0x%X, GLenum attachment = 0x%X, GLenum renderbuffertarget = 0x%X, "
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002216 "GLuint renderbuffer = %d)", target, attachment, renderbuffertarget, renderbuffer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002217
2218 try
2219 {
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +00002220 if ((target != GL_FRAMEBUFFER && target != GL_DRAW_FRAMEBUFFER_ANGLE && target != GL_READ_FRAMEBUFFER_ANGLE)
daniel@transgaming.com2fa45512011-10-04 18:43:18 +00002221 || (renderbuffertarget != GL_RENDERBUFFER && renderbuffer != 0))
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002222 {
2223 return error(GL_INVALID_ENUM);
2224 }
2225
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002226 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002227
2228 if (context)
2229 {
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +00002230 gl::Framebuffer *framebuffer = NULL;
2231 GLuint framebufferHandle = 0;
2232 if (target == GL_READ_FRAMEBUFFER_ANGLE)
2233 {
2234 framebuffer = context->getReadFramebuffer();
2235 framebufferHandle = context->getReadFramebufferHandle();
2236 }
daniel@transgaming.com2fa45512011-10-04 18:43:18 +00002237 else
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +00002238 {
2239 framebuffer = context->getDrawFramebuffer();
2240 framebufferHandle = context->getDrawFramebufferHandle();
2241 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002242
daniel@transgaming.com2fa45512011-10-04 18:43:18 +00002243 if (!framebuffer || (framebufferHandle == 0 && renderbuffer != 0))
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002244 {
2245 return error(GL_INVALID_OPERATION);
2246 }
2247
2248 switch (attachment)
2249 {
2250 case GL_COLOR_ATTACHMENT0:
2251 framebuffer->setColorbuffer(GL_RENDERBUFFER, renderbuffer);
2252 break;
2253 case GL_DEPTH_ATTACHMENT:
2254 framebuffer->setDepthbuffer(GL_RENDERBUFFER, renderbuffer);
2255 break;
2256 case GL_STENCIL_ATTACHMENT:
2257 framebuffer->setStencilbuffer(GL_RENDERBUFFER, renderbuffer);
2258 break;
2259 default:
2260 return error(GL_INVALID_ENUM);
2261 }
2262 }
2263 }
2264 catch(std::bad_alloc&)
2265 {
2266 return error(GL_OUT_OF_MEMORY);
2267 }
2268}
2269
2270void __stdcall glFramebufferTexture2D(GLenum target, GLenum attachment, GLenum textarget, GLuint texture, GLint level)
2271{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002272 EVENT("(GLenum target = 0x%X, GLenum attachment = 0x%X, GLenum textarget = 0x%X, "
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002273 "GLuint texture = %d, GLint level = %d)", target, attachment, textarget, texture, level);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002274
2275 try
2276 {
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +00002277 if (target != GL_FRAMEBUFFER && target != GL_DRAW_FRAMEBUFFER_ANGLE && target != GL_READ_FRAMEBUFFER_ANGLE)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002278 {
2279 return error(GL_INVALID_ENUM);
2280 }
2281
2282 switch (attachment)
2283 {
2284 case GL_COLOR_ATTACHMENT0:
daniel@transgaming.comfbc09532010-04-26 15:33:41 +00002285 case GL_DEPTH_ATTACHMENT:
2286 case GL_STENCIL_ATTACHMENT:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002287 break;
2288 default:
2289 return error(GL_INVALID_ENUM);
2290 }
2291
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002292 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002293
2294 if (context)
2295 {
daniel@transgaming.com93a81472010-04-20 18:52:58 +00002296 if (texture == 0)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002297 {
daniel@transgaming.com93a81472010-04-20 18:52:58 +00002298 textarget = GL_NONE;
2299 }
2300 else
2301 {
2302 gl::Texture *tex = context->getTexture(texture);
2303
2304 if (tex == NULL)
2305 {
2306 return error(GL_INVALID_OPERATION);
2307 }
2308
daniel@transgaming.com01868132010-08-24 19:21:17 +00002309 if (tex->isCompressed())
2310 {
2311 return error(GL_INVALID_OPERATION);
2312 }
2313
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002314 switch (textarget)
2315 {
2316 case GL_TEXTURE_2D:
daniel@transgaming.com93a81472010-04-20 18:52:58 +00002317 if (tex->getTarget() != GL_TEXTURE_2D)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002318 {
2319 return error(GL_INVALID_OPERATION);
2320 }
2321 break;
daniel@transgaming.com93a81472010-04-20 18:52:58 +00002322
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002323 case GL_TEXTURE_CUBE_MAP_POSITIVE_X:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002324 case GL_TEXTURE_CUBE_MAP_NEGATIVE_X:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002325 case GL_TEXTURE_CUBE_MAP_POSITIVE_Y:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002326 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002327 case GL_TEXTURE_CUBE_MAP_POSITIVE_Z:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002328 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z:
daniel@transgaming.com93a81472010-04-20 18:52:58 +00002329 if (tex->getTarget() != GL_TEXTURE_CUBE_MAP)
2330 {
2331 return error(GL_INVALID_OPERATION);
2332 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002333 break;
daniel@transgaming.com93a81472010-04-20 18:52:58 +00002334
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002335 default:
2336 return error(GL_INVALID_ENUM);
2337 }
2338
2339 if (level != 0)
2340 {
2341 return error(GL_INVALID_VALUE);
2342 }
2343 }
2344
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +00002345 gl::Framebuffer *framebuffer = NULL;
2346 GLuint framebufferHandle = 0;
2347 if (target == GL_READ_FRAMEBUFFER_ANGLE)
2348 {
2349 framebuffer = context->getReadFramebuffer();
2350 framebufferHandle = context->getReadFramebufferHandle();
2351 }
2352 else
2353 {
2354 framebuffer = context->getDrawFramebuffer();
2355 framebufferHandle = context->getDrawFramebufferHandle();
2356 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002357
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +00002358 if (framebufferHandle == 0 || !framebuffer)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002359 {
2360 return error(GL_INVALID_OPERATION);
2361 }
2362
daniel@transgaming.comfbc09532010-04-26 15:33:41 +00002363 switch (attachment)
2364 {
2365 case GL_COLOR_ATTACHMENT0: framebuffer->setColorbuffer(textarget, texture); break;
2366 case GL_DEPTH_ATTACHMENT: framebuffer->setDepthbuffer(textarget, texture); break;
2367 case GL_STENCIL_ATTACHMENT: framebuffer->setStencilbuffer(textarget, texture); break;
2368 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002369 }
2370 }
2371 catch(std::bad_alloc&)
2372 {
2373 return error(GL_OUT_OF_MEMORY);
2374 }
2375}
2376
2377void __stdcall glFrontFace(GLenum mode)
2378{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002379 EVENT("(GLenum mode = 0x%X)", mode);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002380
2381 try
2382 {
2383 switch (mode)
2384 {
2385 case GL_CW:
2386 case GL_CCW:
2387 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002388 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002389
2390 if (context)
2391 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00002392 context->setFrontFace(mode);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002393 }
2394 }
2395 break;
2396 default:
2397 return error(GL_INVALID_ENUM);
2398 }
2399 }
2400 catch(std::bad_alloc&)
2401 {
2402 return error(GL_OUT_OF_MEMORY);
2403 }
2404}
2405
2406void __stdcall glGenBuffers(GLsizei n, GLuint* buffers)
2407{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002408 EVENT("(GLsizei n = %d, GLuint* buffers = 0x%0.8p)", n, buffers);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002409
2410 try
2411 {
2412 if (n < 0)
2413 {
2414 return error(GL_INVALID_VALUE);
2415 }
2416
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002417 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002418
2419 if (context)
2420 {
2421 for (int i = 0; i < n; i++)
2422 {
2423 buffers[i] = context->createBuffer();
2424 }
2425 }
2426 }
2427 catch(std::bad_alloc&)
2428 {
2429 return error(GL_OUT_OF_MEMORY);
2430 }
2431}
2432
2433void __stdcall glGenerateMipmap(GLenum target)
2434{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002435 EVENT("(GLenum target = 0x%X)", target);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002436
2437 try
2438 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002439 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com8fd99e22010-04-20 18:52:00 +00002440
2441 if (context)
2442 {
2443 gl::Texture *texture;
2444
2445 switch (target)
2446 {
2447 case GL_TEXTURE_2D:
2448 texture = context->getTexture2D();
2449 break;
2450
2451 case GL_TEXTURE_CUBE_MAP:
2452 texture = context->getTextureCubeMap();
2453 break;
2454
2455 default:
2456 return error(GL_INVALID_ENUM);
2457 }
2458
daniel@transgaming.com01868132010-08-24 19:21:17 +00002459 if (texture->isCompressed())
2460 {
2461 return error(GL_INVALID_OPERATION);
2462 }
2463
daniel@transgaming.com8fd99e22010-04-20 18:52:00 +00002464 texture->generateMipmaps();
2465 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002466 }
2467 catch(std::bad_alloc&)
2468 {
2469 return error(GL_OUT_OF_MEMORY);
2470 }
2471}
2472
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00002473void __stdcall glGenFencesNV(GLsizei n, GLuint* fences)
2474{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002475 EVENT("(GLsizei n = %d, GLuint* fences = 0x%0.8p)", n, fences);
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00002476
2477 try
2478 {
2479 if (n < 0)
2480 {
2481 return error(GL_INVALID_VALUE);
2482 }
2483
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002484 gl::Context *context = gl::getNonLostContext();
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00002485
2486 if (context)
2487 {
2488 for (int i = 0; i < n; i++)
2489 {
2490 fences[i] = context->createFence();
2491 }
2492 }
2493 }
2494 catch(std::bad_alloc&)
2495 {
2496 return error(GL_OUT_OF_MEMORY);
2497 }
2498}
2499
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002500void __stdcall glGenFramebuffers(GLsizei n, GLuint* framebuffers)
2501{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002502 EVENT("(GLsizei n = %d, GLuint* framebuffers = 0x%0.8p)", n, framebuffers);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002503
2504 try
2505 {
2506 if (n < 0)
2507 {
2508 return error(GL_INVALID_VALUE);
2509 }
2510
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002511 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002512
2513 if (context)
2514 {
2515 for (int i = 0; i < n; i++)
2516 {
2517 framebuffers[i] = context->createFramebuffer();
2518 }
2519 }
2520 }
2521 catch(std::bad_alloc&)
2522 {
2523 return error(GL_OUT_OF_MEMORY);
2524 }
2525}
2526
daniel@transgaming.com86bdb822012-01-20 18:24:39 +00002527void __stdcall glGenQueriesEXT(GLsizei n, GLuint* ids)
2528{
2529 EVENT("(GLsizei n = %d, GLuint* ids = 0x%0.8p)", n, ids);
2530
2531 try
2532 {
2533 if (n < 0)
2534 {
2535 return error(GL_INVALID_VALUE);
2536 }
2537
2538 gl::Context *context = gl::getNonLostContext();
2539
2540 if (context)
2541 {
2542 for (int i = 0; i < n; i++)
2543 {
2544 ids[i] = context->createQuery();
2545 }
2546 }
2547 }
2548 catch(std::bad_alloc&)
2549 {
2550 return error(GL_OUT_OF_MEMORY);
2551 }
2552}
2553
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002554void __stdcall glGenRenderbuffers(GLsizei n, GLuint* renderbuffers)
2555{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002556 EVENT("(GLsizei n = %d, GLuint* renderbuffers = 0x%0.8p)", n, renderbuffers);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002557
2558 try
2559 {
2560 if (n < 0)
2561 {
2562 return error(GL_INVALID_VALUE);
2563 }
2564
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002565 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002566
2567 if (context)
2568 {
2569 for (int i = 0; i < n; i++)
2570 {
2571 renderbuffers[i] = context->createRenderbuffer();
2572 }
2573 }
2574 }
2575 catch(std::bad_alloc&)
2576 {
2577 return error(GL_OUT_OF_MEMORY);
2578 }
2579}
2580
2581void __stdcall glGenTextures(GLsizei n, GLuint* textures)
2582{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002583 EVENT("(GLsizei n = %d, GLuint* textures = 0x%0.8p)", n, textures);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002584
2585 try
2586 {
2587 if (n < 0)
2588 {
2589 return error(GL_INVALID_VALUE);
2590 }
2591
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002592 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002593
2594 if (context)
2595 {
2596 for (int i = 0; i < n; i++)
2597 {
2598 textures[i] = context->createTexture();
2599 }
2600 }
2601 }
2602 catch(std::bad_alloc&)
2603 {
2604 return error(GL_OUT_OF_MEMORY);
2605 }
2606}
2607
daniel@transgaming.com85423182010-04-22 13:35:27 +00002608void __stdcall glGetActiveAttrib(GLuint program, GLuint index, GLsizei bufsize, GLsizei *length, GLint *size, GLenum *type, GLchar *name)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002609{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002610 EVENT("(GLuint program = %d, GLuint index = %d, GLsizei bufsize = %d, GLsizei *length = 0x%0.8p, "
daniel@transgaming.com85423182010-04-22 13:35:27 +00002611 "GLint *size = 0x%0.8p, GLenum *type = %0.8p, GLchar *name = %0.8p)",
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002612 program, index, bufsize, length, size, type, name);
2613
2614 try
2615 {
2616 if (bufsize < 0)
2617 {
2618 return error(GL_INVALID_VALUE);
2619 }
2620
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002621 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com85423182010-04-22 13:35:27 +00002622
2623 if (context)
2624 {
2625 gl::Program *programObject = context->getProgram(program);
2626
2627 if (!programObject)
2628 {
2629 if (context->getShader(program))
2630 {
2631 return error(GL_INVALID_OPERATION);
2632 }
2633 else
2634 {
2635 return error(GL_INVALID_VALUE);
2636 }
2637 }
2638
daniel@transgaming.com09fbfef2010-04-22 13:35:31 +00002639 if (index >= (GLuint)programObject->getActiveAttributeCount())
daniel@transgaming.com85423182010-04-22 13:35:27 +00002640 {
2641 return error(GL_INVALID_VALUE);
2642 }
2643
2644 programObject->getActiveAttribute(index, bufsize, length, size, type, name);
2645 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002646 }
2647 catch(std::bad_alloc&)
2648 {
2649 return error(GL_OUT_OF_MEMORY);
2650 }
2651}
2652
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002653void __stdcall glGetActiveUniform(GLuint program, GLuint index, GLsizei bufsize, GLsizei* length, GLint* size, GLenum* type, GLchar* name)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002654{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002655 EVENT("(GLuint program = %d, GLuint index = %d, GLsizei bufsize = %d, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002656 "GLsizei* length = 0x%0.8p, GLint* size = 0x%0.8p, GLenum* type = 0x%0.8p, GLchar* name = 0x%0.8p)",
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002657 program, index, bufsize, length, size, type, name);
2658
2659 try
2660 {
2661 if (bufsize < 0)
2662 {
2663 return error(GL_INVALID_VALUE);
2664 }
2665
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002666 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com09fbfef2010-04-22 13:35:31 +00002667
2668 if (context)
2669 {
2670 gl::Program *programObject = context->getProgram(program);
2671
2672 if (!programObject)
2673 {
2674 if (context->getShader(program))
2675 {
2676 return error(GL_INVALID_OPERATION);
2677 }
2678 else
2679 {
2680 return error(GL_INVALID_VALUE);
2681 }
2682 }
2683
2684 if (index >= (GLuint)programObject->getActiveUniformCount())
2685 {
2686 return error(GL_INVALID_VALUE);
2687 }
2688
2689 programObject->getActiveUniform(index, bufsize, length, size, type, name);
2690 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002691 }
2692 catch(std::bad_alloc&)
2693 {
2694 return error(GL_OUT_OF_MEMORY);
2695 }
2696}
2697
2698void __stdcall glGetAttachedShaders(GLuint program, GLsizei maxcount, GLsizei* count, GLuint* shaders)
2699{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002700 EVENT("(GLuint program = %d, GLsizei maxcount = %d, GLsizei* count = 0x%0.8p, GLuint* shaders = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002701 program, maxcount, count, shaders);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002702
2703 try
2704 {
2705 if (maxcount < 0)
2706 {
2707 return error(GL_INVALID_VALUE);
2708 }
2709
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002710 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com6c785212010-03-30 03:36:17 +00002711
2712 if (context)
2713 {
2714 gl::Program *programObject = context->getProgram(program);
2715
2716 if (!programObject)
2717 {
daniel@transgaming.com23953e32010-04-13 19:53:31 +00002718 if (context->getShader(program))
2719 {
2720 return error(GL_INVALID_OPERATION);
2721 }
2722 else
2723 {
2724 return error(GL_INVALID_VALUE);
2725 }
daniel@transgaming.com6c785212010-03-30 03:36:17 +00002726 }
2727
2728 return programObject->getAttachedShaders(maxcount, count, shaders);
2729 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002730 }
2731 catch(std::bad_alloc&)
2732 {
2733 return error(GL_OUT_OF_MEMORY);
2734 }
2735}
2736
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002737int __stdcall glGetAttribLocation(GLuint program, const GLchar* name)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002738{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002739 EVENT("(GLuint program = %d, const GLchar* name = %s)", program, name);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002740
2741 try
2742 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002743 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002744
2745 if (context)
2746 {
daniel@transgaming.combb274c32010-04-13 03:26:21 +00002747
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002748 gl::Program *programObject = context->getProgram(program);
2749
2750 if (!programObject)
2751 {
daniel@transgaming.combb274c32010-04-13 03:26:21 +00002752 if (context->getShader(program))
2753 {
2754 return error(GL_INVALID_OPERATION, -1);
2755 }
2756 else
2757 {
2758 return error(GL_INVALID_VALUE, -1);
2759 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002760 }
2761
daniel@transgaming.comcf4aa872010-04-13 03:26:27 +00002762 if (!programObject->isLinked())
2763 {
2764 return error(GL_INVALID_OPERATION, -1);
2765 }
2766
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002767 return programObject->getAttributeLocation(name);
2768 }
2769 }
2770 catch(std::bad_alloc&)
2771 {
2772 return error(GL_OUT_OF_MEMORY, -1);
2773 }
2774
2775 return -1;
2776}
2777
2778void __stdcall glGetBooleanv(GLenum pname, GLboolean* params)
2779{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002780 EVENT("(GLenum pname = 0x%X, GLboolean* params = 0x%0.8p)", pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002781
2782 try
2783 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002784 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com777f2672010-04-07 03:25:16 +00002785
2786 if (context)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002787 {
daniel@transgaming.com777f2672010-04-07 03:25:16 +00002788 if (!(context->getBooleanv(pname, params)))
2789 {
2790 GLenum nativeType;
2791 unsigned int numParams = 0;
2792 if (!context->getQueryParameterInfo(pname, &nativeType, &numParams))
2793 return error(GL_INVALID_ENUM);
2794
2795 if (numParams == 0)
2796 return; // it is known that the pname is valid, but there are no parameters to return
2797
2798 if (nativeType == GL_FLOAT)
2799 {
2800 GLfloat *floatParams = NULL;
2801 floatParams = new GLfloat[numParams];
2802
2803 context->getFloatv(pname, floatParams);
2804
2805 for (unsigned int i = 0; i < numParams; ++i)
2806 {
2807 if (floatParams[i] == 0.0f)
2808 params[i] = GL_FALSE;
2809 else
2810 params[i] = GL_TRUE;
2811 }
2812
2813 delete [] floatParams;
2814 }
2815 else if (nativeType == GL_INT)
2816 {
2817 GLint *intParams = NULL;
2818 intParams = new GLint[numParams];
2819
2820 context->getIntegerv(pname, intParams);
2821
2822 for (unsigned int i = 0; i < numParams; ++i)
2823 {
2824 if (intParams[i] == 0)
2825 params[i] = GL_FALSE;
2826 else
2827 params[i] = GL_TRUE;
2828 }
2829
2830 delete [] intParams;
2831 }
2832 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002833 }
2834 }
2835 catch(std::bad_alloc&)
2836 {
2837 return error(GL_OUT_OF_MEMORY);
2838 }
2839}
2840
2841void __stdcall glGetBufferParameteriv(GLenum target, GLenum pname, GLint* params)
2842{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002843 EVENT("(GLenum target = 0x%X, GLenum pname = 0x%X, GLint* params = 0x%0.8p)", target, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002844
2845 try
2846 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002847 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.comaa0ccbd2010-04-15 20:45:05 +00002848
2849 if (context)
2850 {
2851 gl::Buffer *buffer;
2852
2853 switch (target)
2854 {
2855 case GL_ARRAY_BUFFER:
2856 buffer = context->getArrayBuffer();
2857 break;
2858 case GL_ELEMENT_ARRAY_BUFFER:
2859 buffer = context->getElementArrayBuffer();
2860 break;
2861 default: return error(GL_INVALID_ENUM);
2862 }
2863
2864 if (!buffer)
2865 {
2866 // A null buffer means that "0" is bound to the requested buffer target
2867 return error(GL_INVALID_OPERATION);
2868 }
2869
2870 switch (pname)
2871 {
2872 case GL_BUFFER_USAGE:
2873 *params = buffer->usage();
2874 break;
2875 case GL_BUFFER_SIZE:
2876 *params = buffer->size();
2877 break;
2878 default: return error(GL_INVALID_ENUM);
2879 }
2880 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002881 }
2882 catch(std::bad_alloc&)
2883 {
2884 return error(GL_OUT_OF_MEMORY);
2885 }
2886}
2887
2888GLenum __stdcall glGetError(void)
2889{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002890 EVENT("()");
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002891
2892 gl::Context *context = gl::getContext();
2893
2894 if (context)
2895 {
daniel@transgaming.com82b28912011-12-12 21:01:35 +00002896 return context->getError();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002897 }
2898
2899 return GL_NO_ERROR;
2900}
2901
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00002902void __stdcall glGetFenceivNV(GLuint fence, GLenum pname, GLint *params)
2903{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002904 EVENT("(GLuint fence = %d, GLenum pname = 0x%X, GLint *params = 0x%0.8p)", fence, pname, params);
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00002905
2906 try
2907 {
2908
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002909 gl::Context *context = gl::getNonLostContext();
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00002910
2911 if (context)
2912 {
2913 gl::Fence *fenceObject = context->getFence(fence);
2914
2915 if (fenceObject == NULL)
2916 {
2917 return error(GL_INVALID_OPERATION);
2918 }
2919
2920 fenceObject->getFenceiv(pname, params);
2921 }
2922 }
2923 catch(std::bad_alloc&)
2924 {
2925 return error(GL_OUT_OF_MEMORY);
2926 }
2927}
2928
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002929void __stdcall glGetFloatv(GLenum pname, GLfloat* params)
2930{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002931 EVENT("(GLenum pname = 0x%X, GLfloat* params = 0x%0.8p)", pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002932
2933 try
2934 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002935 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com32e58cd2010-03-24 09:44:10 +00002936
2937 if (context)
2938 {
daniel@transgaming.com777f2672010-04-07 03:25:16 +00002939 if (!(context->getFloatv(pname, params)))
daniel@transgaming.com32e58cd2010-03-24 09:44:10 +00002940 {
daniel@transgaming.com777f2672010-04-07 03:25:16 +00002941 GLenum nativeType;
2942 unsigned int numParams = 0;
2943 if (!context->getQueryParameterInfo(pname, &nativeType, &numParams))
2944 return error(GL_INVALID_ENUM);
2945
2946 if (numParams == 0)
2947 return; // it is known that the pname is valid, but that there are no parameters to return.
2948
2949 if (nativeType == GL_BOOL)
2950 {
2951 GLboolean *boolParams = NULL;
2952 boolParams = new GLboolean[numParams];
2953
2954 context->getBooleanv(pname, boolParams);
2955
2956 for (unsigned int i = 0; i < numParams; ++i)
2957 {
2958 if (boolParams[i] == GL_FALSE)
2959 params[i] = 0.0f;
2960 else
2961 params[i] = 1.0f;
2962 }
2963
2964 delete [] boolParams;
2965 }
2966 else if (nativeType == GL_INT)
2967 {
2968 GLint *intParams = NULL;
2969 intParams = new GLint[numParams];
2970
2971 context->getIntegerv(pname, intParams);
2972
2973 for (unsigned int i = 0; i < numParams; ++i)
2974 {
2975 params[i] = (GLfloat)intParams[i];
2976 }
2977
2978 delete [] intParams;
2979 }
daniel@transgaming.com32e58cd2010-03-24 09:44:10 +00002980 }
2981 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002982 }
2983 catch(std::bad_alloc&)
2984 {
2985 return error(GL_OUT_OF_MEMORY);
2986 }
2987}
2988
2989void __stdcall glGetFramebufferAttachmentParameteriv(GLenum target, GLenum attachment, GLenum pname, GLint* params)
2990{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00002991 EVENT("(GLenum target = 0x%X, GLenum attachment = 0x%X, GLenum pname = 0x%X, GLint* params = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002992 target, attachment, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002993
2994 try
2995 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00002996 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002997
2998 if (context)
2999 {
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +00003000 if (target != GL_FRAMEBUFFER && target != GL_DRAW_FRAMEBUFFER_ANGLE && target != GL_READ_FRAMEBUFFER_ANGLE)
daniel@transgaming.comc46c9c02010-04-23 18:34:55 +00003001 {
3002 return error(GL_INVALID_ENUM);
3003 }
3004
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +00003005 gl::Framebuffer *framebuffer = NULL;
3006 if (target == GL_READ_FRAMEBUFFER_ANGLE)
3007 {
3008 if(context->getReadFramebufferHandle() == 0)
3009 {
3010 return error(GL_INVALID_OPERATION);
3011 }
3012
3013 framebuffer = context->getReadFramebuffer();
3014 }
3015 else
3016 {
3017 if (context->getDrawFramebufferHandle() == 0)
3018 {
3019 return error(GL_INVALID_OPERATION);
3020 }
3021
3022 framebuffer = context->getDrawFramebuffer();
3023 }
3024
daniel@transgaming.comc46c9c02010-04-23 18:34:55 +00003025 GLenum attachmentType;
3026 GLuint attachmentHandle;
3027 switch (attachment)
3028 {
3029 case GL_COLOR_ATTACHMENT0:
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +00003030 attachmentType = framebuffer->getColorbufferType();
3031 attachmentHandle = framebuffer->getColorbufferHandle();
daniel@transgaming.comc46c9c02010-04-23 18:34:55 +00003032 break;
3033 case GL_DEPTH_ATTACHMENT:
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +00003034 attachmentType = framebuffer->getDepthbufferType();
3035 attachmentHandle = framebuffer->getDepthbufferHandle();
daniel@transgaming.comc46c9c02010-04-23 18:34:55 +00003036 break;
3037 case GL_STENCIL_ATTACHMENT:
daniel@transgaming.coma27ff1e2010-08-24 19:20:11 +00003038 attachmentType = framebuffer->getStencilbufferType();
3039 attachmentHandle = framebuffer->getStencilbufferHandle();
daniel@transgaming.comc46c9c02010-04-23 18:34:55 +00003040 break;
3041 default: return error(GL_INVALID_ENUM);
3042 }
3043
3044 GLenum attachmentObjectType; // Type category
daniel@transgaming.comfbc09532010-04-26 15:33:41 +00003045 if (attachmentType == GL_NONE || attachmentType == GL_RENDERBUFFER)
daniel@transgaming.comc46c9c02010-04-23 18:34:55 +00003046 {
3047 attachmentObjectType = attachmentType;
3048 }
apatrick@chromium.org551022e2012-01-23 19:56:54 +00003049 else if (gl::IsInternalTextureTarget(attachmentType))
daniel@transgaming.comc46c9c02010-04-23 18:34:55 +00003050 {
3051 attachmentObjectType = GL_TEXTURE;
3052 }
apatrick@chromium.orga1d80592012-01-25 21:52:10 +00003053 else
3054 {
3055 UNREACHABLE();
3056 return;
3057 }
daniel@transgaming.comc46c9c02010-04-23 18:34:55 +00003058
3059 switch (pname)
3060 {
3061 case GL_FRAMEBUFFER_ATTACHMENT_OBJECT_TYPE:
3062 *params = attachmentObjectType;
3063 break;
3064 case GL_FRAMEBUFFER_ATTACHMENT_OBJECT_NAME:
3065 if (attachmentObjectType == GL_RENDERBUFFER || attachmentObjectType == GL_TEXTURE)
3066 {
3067 *params = attachmentHandle;
3068 }
3069 else
3070 {
3071 return error(GL_INVALID_ENUM);
3072 }
3073 break;
3074 case GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_LEVEL:
3075 if (attachmentObjectType == GL_TEXTURE)
3076 {
3077 *params = 0; // FramebufferTexture2D will not allow level to be set to anything else in GL ES 2.0
3078 }
3079 else
3080 {
3081 return error(GL_INVALID_ENUM);
3082 }
3083 break;
3084 case GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_CUBE_MAP_FACE:
3085 if (attachmentObjectType == GL_TEXTURE)
3086 {
daniel@transgaming.com19ffc242010-05-04 03:35:21 +00003087 if (gl::IsCubemapTextureTarget(attachmentType))
daniel@transgaming.comc46c9c02010-04-23 18:34:55 +00003088 {
3089 *params = attachmentType;
3090 }
3091 else
3092 {
3093 *params = 0;
3094 }
3095 }
3096 else
3097 {
3098 return error(GL_INVALID_ENUM);
3099 }
3100 break;
3101 default:
3102 return error(GL_INVALID_ENUM);
3103 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003104 }
3105 }
3106 catch(std::bad_alloc&)
3107 {
3108 return error(GL_OUT_OF_MEMORY);
3109 }
3110}
3111
daniel@transgaming.com17f548c2011-11-09 17:47:02 +00003112GLenum __stdcall glGetGraphicsResetStatusEXT(void)
3113{
3114 EVENT("()");
3115
3116 try
3117 {
3118 gl::Context *context = gl::getContext();
3119
3120 if (context)
3121 {
3122 return context->getResetStatus();
3123 }
3124
3125 return GL_NO_ERROR;
3126 }
3127 catch(std::bad_alloc&)
3128 {
3129 return GL_OUT_OF_MEMORY;
3130 }
3131}
3132
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003133void __stdcall glGetIntegerv(GLenum pname, GLint* params)
3134{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00003135 EVENT("(GLenum pname = 0x%X, GLint* params = 0x%0.8p)", pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003136
3137 try
3138 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00003139 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003140
3141 if (context)
3142 {
daniel@transgaming.com777f2672010-04-07 03:25:16 +00003143 if (!(context->getIntegerv(pname, params)))
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003144 {
daniel@transgaming.com777f2672010-04-07 03:25:16 +00003145 GLenum nativeType;
3146 unsigned int numParams = 0;
3147 if (!context->getQueryParameterInfo(pname, &nativeType, &numParams))
3148 return error(GL_INVALID_ENUM);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003149
daniel@transgaming.com777f2672010-04-07 03:25:16 +00003150 if (numParams == 0)
3151 return; // it is known that pname is valid, but there are no parameters to return
3152
3153 if (nativeType == GL_BOOL)
3154 {
3155 GLboolean *boolParams = NULL;
3156 boolParams = new GLboolean[numParams];
3157
3158 context->getBooleanv(pname, boolParams);
3159
3160 for (unsigned int i = 0; i < numParams; ++i)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003161 {
daniel@transgaming.com777f2672010-04-07 03:25:16 +00003162 if (boolParams[i] == GL_FALSE)
3163 params[i] = 0;
3164 else
3165 params[i] = 1;
3166 }
3167
3168 delete [] boolParams;
3169 }
3170 else if (nativeType == GL_FLOAT)
3171 {
3172 GLfloat *floatParams = NULL;
3173 floatParams = new GLfloat[numParams];
3174
3175 context->getFloatv(pname, floatParams);
3176
3177 for (unsigned int i = 0; i < numParams; ++i)
3178 {
daniel@transgaming.comc1641352010-04-26 15:33:36 +00003179 if (pname == GL_DEPTH_RANGE || pname == GL_COLOR_CLEAR_VALUE || pname == GL_DEPTH_CLEAR_VALUE || pname == GL_BLEND_COLOR)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003180 {
daniel@transgaming.com777f2672010-04-07 03:25:16 +00003181 params[i] = (GLint)(((GLfloat)(0xFFFFFFFF) * floatParams[i] - 1.0f) / 2.0f);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003182 }
daniel@transgaming.com777f2672010-04-07 03:25:16 +00003183 else
3184 params[i] = (GLint)(floatParams[i] > 0.0f ? floor(floatParams[i] + 0.5) : ceil(floatParams[i] - 0.5));
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003185 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003186
daniel@transgaming.com777f2672010-04-07 03:25:16 +00003187 delete [] floatParams;
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003188 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003189 }
3190 }
3191 }
3192 catch(std::bad_alloc&)
3193 {
3194 return error(GL_OUT_OF_MEMORY);
3195 }
3196}
3197
3198void __stdcall glGetProgramiv(GLuint program, GLenum pname, GLint* params)
3199{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00003200 EVENT("(GLuint program = %d, GLenum pname = %d, GLint* params = 0x%0.8p)", program, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003201
3202 try
3203 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00003204 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003205
3206 if (context)
3207 {
3208 gl::Program *programObject = context->getProgram(program);
3209
3210 if (!programObject)
3211 {
3212 return error(GL_INVALID_VALUE);
3213 }
3214
3215 switch (pname)
3216 {
3217 case GL_DELETE_STATUS:
daniel@transgaming.comcba50572010-03-28 19:36:09 +00003218 *params = programObject->isFlaggedForDeletion();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003219 return;
3220 case GL_LINK_STATUS:
3221 *params = programObject->isLinked();
3222 return;
3223 case GL_VALIDATE_STATUS:
daniel@transgaming.com86a7a132010-04-29 03:32:32 +00003224 *params = programObject->isValidated();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003225 return;
3226 case GL_INFO_LOG_LENGTH:
daniel@transgaming.comcba50572010-03-28 19:36:09 +00003227 *params = programObject->getInfoLogLength();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003228 return;
3229 case GL_ATTACHED_SHADERS:
daniel@transgaming.comcba50572010-03-28 19:36:09 +00003230 *params = programObject->getAttachedShadersCount();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003231 return;
3232 case GL_ACTIVE_ATTRIBUTES:
daniel@transgaming.com85423182010-04-22 13:35:27 +00003233 *params = programObject->getActiveAttributeCount();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003234 return;
3235 case GL_ACTIVE_ATTRIBUTE_MAX_LENGTH:
daniel@transgaming.com85423182010-04-22 13:35:27 +00003236 *params = programObject->getActiveAttributeMaxLength();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003237 return;
3238 case GL_ACTIVE_UNIFORMS:
daniel@transgaming.com09fbfef2010-04-22 13:35:31 +00003239 *params = programObject->getActiveUniformCount();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003240 return;
3241 case GL_ACTIVE_UNIFORM_MAX_LENGTH:
daniel@transgaming.com09fbfef2010-04-22 13:35:31 +00003242 *params = programObject->getActiveUniformMaxLength();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003243 return;
3244 default:
3245 return error(GL_INVALID_ENUM);
3246 }
3247 }
3248 }
3249 catch(std::bad_alloc&)
3250 {
3251 return error(GL_OUT_OF_MEMORY);
3252 }
3253}
3254
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00003255void __stdcall glGetProgramInfoLog(GLuint program, GLsizei bufsize, GLsizei* length, GLchar* infolog)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003256{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00003257 EVENT("(GLuint program = %d, GLsizei bufsize = %d, GLsizei* length = 0x%0.8p, GLchar* infolog = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003258 program, bufsize, length, infolog);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003259
3260 try
3261 {
3262 if (bufsize < 0)
3263 {
3264 return error(GL_INVALID_VALUE);
3265 }
3266
daniel@transgaming.com9d788502011-11-09 17:46:55 +00003267 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.comcba50572010-03-28 19:36:09 +00003268
3269 if (context)
3270 {
3271 gl::Program *programObject = context->getProgram(program);
3272
3273 if (!programObject)
3274 {
3275 return error(GL_INVALID_VALUE);
3276 }
3277
3278 programObject->getInfoLog(bufsize, length, infolog);
3279 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003280 }
3281 catch(std::bad_alloc&)
3282 {
3283 return error(GL_OUT_OF_MEMORY);
3284 }
3285}
3286
daniel@transgaming.com86bdb822012-01-20 18:24:39 +00003287void __stdcall glGetQueryivEXT(GLenum target, GLenum pname, GLint *params)
3288{
3289 EVENT("GLenum target = 0x%X, GLenum pname = 0x%X, GLint *params = 0x%0.8p)", target, pname, params);
3290
3291 try
3292 {
3293 switch (pname)
3294 {
3295 case GL_CURRENT_QUERY_EXT:
3296 break;
3297 default:
3298 return error(GL_INVALID_ENUM);
3299 }
3300
3301 gl::Context *context = gl::getNonLostContext();
3302
3303 if (context)
3304 {
3305 params[0] = context->getActiveQuery(target);
3306 }
3307 }
3308 catch(std::bad_alloc&)
3309 {
3310 return error(GL_OUT_OF_MEMORY);
3311 }
3312}
3313
3314void __stdcall glGetQueryObjectuivEXT(GLuint id, GLenum pname, GLuint *params)
3315{
3316 EVENT("(GLuint id = %d, GLenum pname = 0x%X, GLuint *params = 0x%0.8p)", id, pname, params);
3317
3318 try
3319 {
3320 switch (pname)
3321 {
3322 case GL_QUERY_RESULT_EXT:
3323 case GL_QUERY_RESULT_AVAILABLE_EXT:
3324 break;
3325 default:
3326 return error(GL_INVALID_ENUM);
3327 }
3328 gl::Context *context = gl::getNonLostContext();
3329
3330 if (context)
3331 {
3332
3333 gl::Query *queryObject = context->getQuery(id, false, GL_NONE);
3334
3335 if (!queryObject)
3336 {
3337 return error(GL_INVALID_OPERATION);
3338 }
3339
3340 if (context->getActiveQuery(queryObject->getType()) == id)
3341 {
3342 return error(GL_INVALID_OPERATION);
3343 }
3344
3345 switch(pname)
3346 {
3347 case GL_QUERY_RESULT_EXT:
3348 params[0] = queryObject->getResult();
3349 break;
3350 case GL_QUERY_RESULT_AVAILABLE_EXT:
3351 params[0] = queryObject->isResultAvailable();
3352 break;
3353 default:
3354 ASSERT(false);
3355 }
3356 }
3357 }
3358 catch(std::bad_alloc&)
3359 {
3360 return error(GL_OUT_OF_MEMORY);
3361 }
3362}
3363
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003364void __stdcall glGetRenderbufferParameteriv(GLenum target, GLenum pname, GLint* params)
3365{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00003366 EVENT("(GLenum target = 0x%X, GLenum pname = 0x%X, GLint* params = 0x%0.8p)", target, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003367
3368 try
3369 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00003370 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4901fca2010-04-20 18:52:41 +00003371
3372 if (context)
3373 {
3374 if (target != GL_RENDERBUFFER)
3375 {
3376 return error(GL_INVALID_ENUM);
3377 }
3378
daniel@transgaming.com428d1582010-05-04 03:35:25 +00003379 if (context->getRenderbufferHandle() == 0)
daniel@transgaming.com4901fca2010-04-20 18:52:41 +00003380 {
3381 return error(GL_INVALID_OPERATION);
3382 }
3383
daniel@transgaming.com428d1582010-05-04 03:35:25 +00003384 gl::Renderbuffer *renderbuffer = context->getRenderbuffer(context->getRenderbufferHandle());
daniel@transgaming.com4901fca2010-04-20 18:52:41 +00003385
3386 switch (pname)
3387 {
daniel@transgaming.comd2fd4f22011-02-01 18:49:11 +00003388 case GL_RENDERBUFFER_WIDTH: *params = renderbuffer->getWidth(); break;
3389 case GL_RENDERBUFFER_HEIGHT: *params = renderbuffer->getHeight(); break;
3390 case GL_RENDERBUFFER_INTERNAL_FORMAT: *params = renderbuffer->getInternalFormat(); break;
3391 case GL_RENDERBUFFER_RED_SIZE: *params = renderbuffer->getRedSize(); break;
3392 case GL_RENDERBUFFER_GREEN_SIZE: *params = renderbuffer->getGreenSize(); break;
3393 case GL_RENDERBUFFER_BLUE_SIZE: *params = renderbuffer->getBlueSize(); break;
3394 case GL_RENDERBUFFER_ALPHA_SIZE: *params = renderbuffer->getAlphaSize(); break;
3395 case GL_RENDERBUFFER_DEPTH_SIZE: *params = renderbuffer->getDepthSize(); break;
3396 case GL_RENDERBUFFER_STENCIL_SIZE: *params = renderbuffer->getStencilSize(); break;
daniel@transgaming.com1f135d82010-08-24 19:20:36 +00003397 case GL_RENDERBUFFER_SAMPLES_ANGLE:
daniel@transgaming.comd2fd4f22011-02-01 18:49:11 +00003398 if (context->getMaxSupportedSamples() != 0)
daniel@transgaming.com1f135d82010-08-24 19:20:36 +00003399 {
daniel@transgaming.comd2fd4f22011-02-01 18:49:11 +00003400 *params = renderbuffer->getSamples();
3401 }
3402 else
3403 {
3404 return error(GL_INVALID_ENUM);
daniel@transgaming.com1f135d82010-08-24 19:20:36 +00003405 }
3406 break;
daniel@transgaming.com4901fca2010-04-20 18:52:41 +00003407 default:
3408 return error(GL_INVALID_ENUM);
3409 }
3410 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003411 }
3412 catch(std::bad_alloc&)
3413 {
3414 return error(GL_OUT_OF_MEMORY);
3415 }
3416}
3417
3418void __stdcall glGetShaderiv(GLuint shader, GLenum pname, GLint* params)
3419{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00003420 EVENT("(GLuint shader = %d, GLenum pname = %d, GLint* params = 0x%0.8p)", shader, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003421
3422 try
3423 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00003424 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003425
3426 if (context)
3427 {
3428 gl::Shader *shaderObject = context->getShader(shader);
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00003429
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003430 if (!shaderObject)
3431 {
3432 return error(GL_INVALID_VALUE);
3433 }
3434
3435 switch (pname)
3436 {
3437 case GL_SHADER_TYPE:
3438 *params = shaderObject->getType();
3439 return;
3440 case GL_DELETE_STATUS:
daniel@transgaming.comcba50572010-03-28 19:36:09 +00003441 *params = shaderObject->isFlaggedForDeletion();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003442 return;
3443 case GL_COMPILE_STATUS:
3444 *params = shaderObject->isCompiled() ? GL_TRUE : GL_FALSE;
3445 return;
3446 case GL_INFO_LOG_LENGTH:
daniel@transgaming.comcba50572010-03-28 19:36:09 +00003447 *params = shaderObject->getInfoLogLength();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003448 return;
3449 case GL_SHADER_SOURCE_LENGTH:
daniel@transgaming.comcba50572010-03-28 19:36:09 +00003450 *params = shaderObject->getSourceLength();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003451 return;
zmo@google.coma574f782011-10-03 21:45:23 +00003452 case GL_TRANSLATED_SHADER_SOURCE_LENGTH_ANGLE:
3453 *params = shaderObject->getTranslatedSourceLength();
3454 return;
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003455 default:
3456 return error(GL_INVALID_ENUM);
3457 }
3458 }
3459 }
3460 catch(std::bad_alloc&)
3461 {
3462 return error(GL_OUT_OF_MEMORY);
3463 }
3464}
3465
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00003466void __stdcall glGetShaderInfoLog(GLuint shader, GLsizei bufsize, GLsizei* length, GLchar* infolog)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003467{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00003468 EVENT("(GLuint shader = %d, GLsizei bufsize = %d, GLsizei* length = 0x%0.8p, GLchar* infolog = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003469 shader, bufsize, length, infolog);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003470
3471 try
3472 {
3473 if (bufsize < 0)
3474 {
3475 return error(GL_INVALID_VALUE);
3476 }
3477
daniel@transgaming.com9d788502011-11-09 17:46:55 +00003478 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.comcba50572010-03-28 19:36:09 +00003479
3480 if (context)
3481 {
3482 gl::Shader *shaderObject = context->getShader(shader);
3483
3484 if (!shaderObject)
3485 {
3486 return error(GL_INVALID_VALUE);
3487 }
3488
3489 shaderObject->getInfoLog(bufsize, length, infolog);
3490 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003491 }
3492 catch(std::bad_alloc&)
3493 {
3494 return error(GL_OUT_OF_MEMORY);
3495 }
3496}
3497
3498void __stdcall glGetShaderPrecisionFormat(GLenum shadertype, GLenum precisiontype, GLint* range, GLint* precision)
3499{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00003500 EVENT("(GLenum shadertype = 0x%X, GLenum precisiontype = 0x%X, GLint* range = 0x%0.8p, GLint* precision = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003501 shadertype, precisiontype, range, precision);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003502
3503 try
3504 {
daniel@transgaming.com6c785212010-03-30 03:36:17 +00003505 switch (shadertype)
3506 {
3507 case GL_VERTEX_SHADER:
3508 case GL_FRAGMENT_SHADER:
3509 break;
3510 default:
3511 return error(GL_INVALID_ENUM);
3512 }
3513
3514 switch (precisiontype)
3515 {
3516 case GL_LOW_FLOAT:
3517 case GL_MEDIUM_FLOAT:
3518 case GL_HIGH_FLOAT:
3519 // Assume IEEE 754 precision
3520 range[0] = 127;
3521 range[1] = 127;
daniel@transgaming.comc5c15382010-04-23 18:34:49 +00003522 *precision = 23;
daniel@transgaming.com6c785212010-03-30 03:36:17 +00003523 break;
3524 case GL_LOW_INT:
3525 case GL_MEDIUM_INT:
3526 case GL_HIGH_INT:
3527 // Some (most) hardware only supports single-precision floating-point numbers,
3528 // which can accurately represent integers up to +/-16777216
3529 range[0] = 24;
3530 range[1] = 24;
daniel@transgaming.comc5c15382010-04-23 18:34:49 +00003531 *precision = 0;
daniel@transgaming.com6c785212010-03-30 03:36:17 +00003532 break;
3533 default:
3534 return error(GL_INVALID_ENUM);
3535 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003536 }
3537 catch(std::bad_alloc&)
3538 {
3539 return error(GL_OUT_OF_MEMORY);
3540 }
3541}
3542
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00003543void __stdcall glGetShaderSource(GLuint shader, GLsizei bufsize, GLsizei* length, GLchar* source)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003544{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00003545 EVENT("(GLuint shader = %d, GLsizei bufsize = %d, GLsizei* length = 0x%0.8p, GLchar* source = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003546 shader, bufsize, length, source);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003547
3548 try
3549 {
3550 if (bufsize < 0)
3551 {
3552 return error(GL_INVALID_VALUE);
3553 }
3554
daniel@transgaming.com9d788502011-11-09 17:46:55 +00003555 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.comcba50572010-03-28 19:36:09 +00003556
3557 if (context)
3558 {
3559 gl::Shader *shaderObject = context->getShader(shader);
3560
3561 if (!shaderObject)
3562 {
daniel@transgaming.com41187f12010-04-01 13:39:29 +00003563 return error(GL_INVALID_OPERATION);
daniel@transgaming.comcba50572010-03-28 19:36:09 +00003564 }
3565
3566 shaderObject->getSource(bufsize, length, source);
3567 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003568 }
3569 catch(std::bad_alloc&)
3570 {
3571 return error(GL_OUT_OF_MEMORY);
3572 }
3573}
3574
zmo@google.coma574f782011-10-03 21:45:23 +00003575void __stdcall glGetTranslatedShaderSourceANGLE(GLuint shader, GLsizei bufsize, GLsizei* length, GLchar* source)
3576{
3577 EVENT("(GLuint shader = %d, GLsizei bufsize = %d, GLsizei* length = 0x%0.8p, GLchar* source = 0x%0.8p)",
3578 shader, bufsize, length, source);
3579
3580 try
3581 {
3582 if (bufsize < 0)
3583 {
3584 return error(GL_INVALID_VALUE);
3585 }
3586
daniel@transgaming.com9d788502011-11-09 17:46:55 +00003587 gl::Context *context = gl::getNonLostContext();
zmo@google.coma574f782011-10-03 21:45:23 +00003588
3589 if (context)
3590 {
3591 gl::Shader *shaderObject = context->getShader(shader);
3592
3593 if (!shaderObject)
3594 {
3595 return error(GL_INVALID_OPERATION);
3596 }
3597
3598 shaderObject->getTranslatedSource(bufsize, length, source);
3599 }
3600 }
3601 catch(std::bad_alloc&)
3602 {
3603 return error(GL_OUT_OF_MEMORY);
3604 }
3605}
3606
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003607const GLubyte* __stdcall glGetString(GLenum name)
3608{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00003609 EVENT("(GLenum name = 0x%X)", name);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003610
3611 try
3612 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00003613 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com3e4c6002010-05-05 18:50:13 +00003614
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003615 switch (name)
3616 {
3617 case GL_VENDOR:
daniel@transgaming.coma0ce7e62011-01-25 14:47:16 +00003618 return (GLubyte*)"Google Inc.";
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003619 case GL_RENDERER:
daniel@transgaming.comc23ff642011-08-16 20:28:45 +00003620 return (GLubyte*)((context != NULL) ? context->getRendererString() : "ANGLE");
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003621 case GL_VERSION:
daniel@transgaming.coma0ce7e62011-01-25 14:47:16 +00003622 return (GLubyte*)"OpenGL ES 2.0 (ANGLE "VERSION_STRING")";
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003623 case GL_SHADING_LANGUAGE_VERSION:
daniel@transgaming.coma0ce7e62011-01-25 14:47:16 +00003624 return (GLubyte*)"OpenGL ES GLSL ES 1.00 (ANGLE "VERSION_STRING")";
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003625 case GL_EXTENSIONS:
daniel@transgaming.com3e4c6002010-05-05 18:50:13 +00003626 return (GLubyte*)((context != NULL) ? context->getExtensionString() : "");
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003627 default:
3628 return error(GL_INVALID_ENUM, (GLubyte*)NULL);
3629 }
3630 }
3631 catch(std::bad_alloc&)
3632 {
3633 return error(GL_OUT_OF_MEMORY, (GLubyte*)NULL);
3634 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003635}
3636
3637void __stdcall glGetTexParameterfv(GLenum target, GLenum pname, GLfloat* params)
3638{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00003639 EVENT("(GLenum target = 0x%X, GLenum pname = 0x%X, GLfloat* params = 0x%0.8p)", target, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003640
3641 try
3642 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00003643 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com5d2bee92010-04-20 18:51:56 +00003644
3645 if (context)
3646 {
3647 gl::Texture *texture;
3648
3649 switch (target)
3650 {
3651 case GL_TEXTURE_2D:
3652 texture = context->getTexture2D();
3653 break;
3654 case GL_TEXTURE_CUBE_MAP:
3655 texture = context->getTextureCubeMap();
3656 break;
3657 default:
3658 return error(GL_INVALID_ENUM);
3659 }
3660
3661 switch (pname)
3662 {
3663 case GL_TEXTURE_MAG_FILTER:
3664 *params = (GLfloat)texture->getMagFilter();
3665 break;
3666 case GL_TEXTURE_MIN_FILTER:
3667 *params = (GLfloat)texture->getMinFilter();
3668 break;
3669 case GL_TEXTURE_WRAP_S:
3670 *params = (GLfloat)texture->getWrapS();
3671 break;
3672 case GL_TEXTURE_WRAP_T:
3673 *params = (GLfloat)texture->getWrapT();
3674 break;
daniel@transgaming.comd30bd0a2011-11-11 04:10:34 +00003675 case GL_TEXTURE_IMMUTABLE_FORMAT_EXT:
3676 *params = (GLfloat)(texture->isImmutable() ? GL_TRUE : GL_FALSE);
3677 break;
daniel@transgaming.com7d18c172011-11-11 04:18:21 +00003678 case GL_TEXTURE_USAGE_ANGLE:
3679 *params = (GLfloat)texture->getUsage();
3680 break;
daniel@transgaming.com5d2bee92010-04-20 18:51:56 +00003681 default:
3682 return error(GL_INVALID_ENUM);
3683 }
3684 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003685 }
3686 catch(std::bad_alloc&)
3687 {
3688 return error(GL_OUT_OF_MEMORY);
3689 }
3690}
3691
3692void __stdcall glGetTexParameteriv(GLenum target, GLenum pname, GLint* params)
3693{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00003694 EVENT("(GLenum target = 0x%X, GLenum pname = 0x%X, GLint* params = 0x%0.8p)", target, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003695
3696 try
3697 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00003698 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com5d2bee92010-04-20 18:51:56 +00003699
3700 if (context)
3701 {
3702 gl::Texture *texture;
3703
3704 switch (target)
3705 {
3706 case GL_TEXTURE_2D:
3707 texture = context->getTexture2D();
3708 break;
3709 case GL_TEXTURE_CUBE_MAP:
3710 texture = context->getTextureCubeMap();
3711 break;
3712 default:
3713 return error(GL_INVALID_ENUM);
3714 }
3715
3716 switch (pname)
3717 {
3718 case GL_TEXTURE_MAG_FILTER:
3719 *params = texture->getMagFilter();
3720 break;
3721 case GL_TEXTURE_MIN_FILTER:
3722 *params = texture->getMinFilter();
3723 break;
3724 case GL_TEXTURE_WRAP_S:
3725 *params = texture->getWrapS();
3726 break;
3727 case GL_TEXTURE_WRAP_T:
3728 *params = texture->getWrapT();
3729 break;
daniel@transgaming.comd30bd0a2011-11-11 04:10:34 +00003730 case GL_TEXTURE_IMMUTABLE_FORMAT_EXT:
3731 *params = texture->isImmutable() ? GL_TRUE : GL_FALSE;
3732 break;
daniel@transgaming.com7d18c172011-11-11 04:18:21 +00003733 case GL_TEXTURE_USAGE_ANGLE:
3734 *params = texture->getUsage();
3735 break;
daniel@transgaming.com5d2bee92010-04-20 18:51:56 +00003736 default:
3737 return error(GL_INVALID_ENUM);
3738 }
3739 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003740 }
3741 catch(std::bad_alloc&)
3742 {
3743 return error(GL_OUT_OF_MEMORY);
3744 }
3745}
3746
daniel@transgaming.com9a849122011-11-12 03:18:00 +00003747void __stdcall glGetnUniformfvEXT(GLuint program, GLint location, GLsizei bufSize, GLfloat* params)
3748{
3749 EVENT("(GLuint program = %d, GLint location = %d, GLsizei bufSize = %d, GLfloat* params = 0x%0.8p)",
3750 program, location, bufSize, params);
3751
3752 try
3753 {
3754 if (bufSize < 0)
3755 {
3756 return error(GL_INVALID_VALUE);
3757 }
3758
3759 gl::Context *context = gl::getNonLostContext();
3760
3761 if (context)
3762 {
3763 if (program == 0)
3764 {
3765 return error(GL_INVALID_VALUE);
3766 }
3767
3768 gl::Program *programObject = context->getProgram(program);
3769
3770 if (!programObject || !programObject->isLinked())
3771 {
3772 return error(GL_INVALID_OPERATION);
3773 }
3774
3775 if (!programObject->getUniformfv(location, &bufSize, params))
3776 {
3777 return error(GL_INVALID_OPERATION);
3778 }
3779 }
3780 }
3781 catch(std::bad_alloc&)
3782 {
3783 return error(GL_OUT_OF_MEMORY);
3784 }
3785}
3786
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003787void __stdcall glGetUniformfv(GLuint program, GLint location, GLfloat* params)
3788{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00003789 EVENT("(GLuint program = %d, GLint location = %d, GLfloat* params = 0x%0.8p)", program, location, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003790
3791 try
3792 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00003793 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.combb3d9d02010-04-13 03:26:06 +00003794
3795 if (context)
3796 {
3797 if (program == 0)
3798 {
3799 return error(GL_INVALID_VALUE);
3800 }
3801
3802 gl::Program *programObject = context->getProgram(program);
3803
3804 if (!programObject || !programObject->isLinked())
3805 {
3806 return error(GL_INVALID_OPERATION);
3807 }
3808
daniel@transgaming.com9a849122011-11-12 03:18:00 +00003809 if (!programObject->getUniformfv(location, NULL, params))
3810 {
3811 return error(GL_INVALID_OPERATION);
3812 }
3813 }
3814 }
3815 catch(std::bad_alloc&)
3816 {
3817 return error(GL_OUT_OF_MEMORY);
3818 }
3819}
3820
3821void __stdcall glGetnUniformivEXT(GLuint program, GLint location, GLsizei bufSize, GLint* params)
3822{
3823 EVENT("(GLuint program = %d, GLint location = %d, GLsizei bufSize = %d, GLint* params = 0x%0.8p)",
3824 program, location, bufSize, params);
3825
3826 try
3827 {
3828 if (bufSize < 0)
3829 {
3830 return error(GL_INVALID_VALUE);
3831 }
3832
3833 gl::Context *context = gl::getNonLostContext();
3834
3835 if (context)
3836 {
3837 if (program == 0)
3838 {
3839 return error(GL_INVALID_VALUE);
3840 }
3841
3842 gl::Program *programObject = context->getProgram(program);
3843
3844 if (!programObject || !programObject->isLinked())
3845 {
3846 return error(GL_INVALID_OPERATION);
3847 }
3848
3849 if (!programObject)
3850 {
3851 return error(GL_INVALID_OPERATION);
3852 }
3853
3854 if (!programObject->getUniformiv(location, &bufSize, params))
daniel@transgaming.combb3d9d02010-04-13 03:26:06 +00003855 {
3856 return error(GL_INVALID_OPERATION);
3857 }
3858 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003859 }
3860 catch(std::bad_alloc&)
3861 {
3862 return error(GL_OUT_OF_MEMORY);
3863 }
3864}
3865
3866void __stdcall glGetUniformiv(GLuint program, GLint location, GLint* params)
3867{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00003868 EVENT("(GLuint program = %d, GLint location = %d, GLint* params = 0x%0.8p)", program, location, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003869
3870 try
3871 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00003872 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.combb3d9d02010-04-13 03:26:06 +00003873
3874 if (context)
3875 {
3876 if (program == 0)
3877 {
3878 return error(GL_INVALID_VALUE);
3879 }
3880
3881 gl::Program *programObject = context->getProgram(program);
3882
3883 if (!programObject || !programObject->isLinked())
3884 {
3885 return error(GL_INVALID_OPERATION);
3886 }
3887
3888 if (!programObject)
3889 {
3890 return error(GL_INVALID_OPERATION);
3891 }
3892
daniel@transgaming.com9a849122011-11-12 03:18:00 +00003893 if (!programObject->getUniformiv(location, NULL, params))
daniel@transgaming.combb3d9d02010-04-13 03:26:06 +00003894 {
3895 return error(GL_INVALID_OPERATION);
3896 }
3897 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003898 }
3899 catch(std::bad_alloc&)
3900 {
3901 return error(GL_OUT_OF_MEMORY);
3902 }
3903}
3904
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00003905int __stdcall glGetUniformLocation(GLuint program, const GLchar* name)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003906{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00003907 EVENT("(GLuint program = %d, const GLchar* name = 0x%0.8p)", program, name);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003908
3909 try
3910 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00003911 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003912
3913 if (strstr(name, "gl_") == name)
3914 {
3915 return -1;
3916 }
3917
3918 if (context)
3919 {
3920 gl::Program *programObject = context->getProgram(program);
3921
3922 if (!programObject)
3923 {
daniel@transgaming.comd1abe5b2010-04-13 19:53:33 +00003924 if (context->getShader(program))
3925 {
3926 return error(GL_INVALID_OPERATION, -1);
3927 }
3928 else
3929 {
3930 return error(GL_INVALID_VALUE, -1);
3931 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003932 }
3933
3934 if (!programObject->isLinked())
3935 {
3936 return error(GL_INVALID_OPERATION, -1);
3937 }
3938
daniel@transgaming.com024f1a92011-09-20 16:06:25 +00003939 return programObject->getUniformLocation(name);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003940 }
3941 }
3942 catch(std::bad_alloc&)
3943 {
3944 return error(GL_OUT_OF_MEMORY, -1);
3945 }
3946
3947 return -1;
3948}
3949
3950void __stdcall glGetVertexAttribfv(GLuint index, GLenum pname, GLfloat* params)
3951{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00003952 EVENT("(GLuint index = %d, GLenum pname = 0x%X, GLfloat* params = 0x%0.8p)", index, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003953
3954 try
3955 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00003956 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003957
daniel@transgaming.come0078962010-04-15 20:45:08 +00003958 if (context)
3959 {
3960 if (index >= gl::MAX_VERTEX_ATTRIBS)
3961 {
3962 return error(GL_INVALID_VALUE);
3963 }
3964
daniel@transgaming.com83921382011-01-08 05:46:00 +00003965 const gl::VertexAttribute &attribState = context->getVertexAttribState(index);
daniel@transgaming.com428d1582010-05-04 03:35:25 +00003966
daniel@transgaming.come0078962010-04-15 20:45:08 +00003967 switch (pname)
3968 {
3969 case GL_VERTEX_ATTRIB_ARRAY_ENABLED:
daniel@transgaming.com83921382011-01-08 05:46:00 +00003970 *params = (GLfloat)(attribState.mArrayEnabled ? GL_TRUE : GL_FALSE);
daniel@transgaming.come0078962010-04-15 20:45:08 +00003971 break;
3972 case GL_VERTEX_ATTRIB_ARRAY_SIZE:
daniel@transgaming.com428d1582010-05-04 03:35:25 +00003973 *params = (GLfloat)attribState.mSize;
daniel@transgaming.come0078962010-04-15 20:45:08 +00003974 break;
3975 case GL_VERTEX_ATTRIB_ARRAY_STRIDE:
daniel@transgaming.com428d1582010-05-04 03:35:25 +00003976 *params = (GLfloat)attribState.mStride;
daniel@transgaming.come0078962010-04-15 20:45:08 +00003977 break;
3978 case GL_VERTEX_ATTRIB_ARRAY_TYPE:
daniel@transgaming.com428d1582010-05-04 03:35:25 +00003979 *params = (GLfloat)attribState.mType;
daniel@transgaming.come0078962010-04-15 20:45:08 +00003980 break;
3981 case GL_VERTEX_ATTRIB_ARRAY_NORMALIZED:
daniel@transgaming.com428d1582010-05-04 03:35:25 +00003982 *params = (GLfloat)(attribState.mNormalized ? GL_TRUE : GL_FALSE);
daniel@transgaming.come0078962010-04-15 20:45:08 +00003983 break;
3984 case GL_VERTEX_ATTRIB_ARRAY_BUFFER_BINDING:
daniel@transgaming.com9ecb9f92010-07-28 19:21:12 +00003985 *params = (GLfloat)attribState.mBoundBuffer.id();
daniel@transgaming.come0078962010-04-15 20:45:08 +00003986 break;
3987 case GL_CURRENT_VERTEX_ATTRIB:
3988 for (int i = 0; i < 4; ++i)
3989 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00003990 params[i] = attribState.mCurrentValue[i];
daniel@transgaming.come0078962010-04-15 20:45:08 +00003991 }
3992 break;
daniel@transgaming.comd2820bf2012-01-27 15:38:48 +00003993 case GL_VERTEX_ATTRIB_ARRAY_DIVISOR_ANGLE:
3994 *params = (GLfloat)attribState.mDivisor;
3995 break;
daniel@transgaming.come0078962010-04-15 20:45:08 +00003996 default: return error(GL_INVALID_ENUM);
3997 }
3998 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003999 }
4000 catch(std::bad_alloc&)
4001 {
4002 return error(GL_OUT_OF_MEMORY);
4003 }
4004}
4005
4006void __stdcall glGetVertexAttribiv(GLuint index, GLenum pname, GLint* params)
4007{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004008 EVENT("(GLuint index = %d, GLenum pname = 0x%X, GLint* params = 0x%0.8p)", index, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004009
4010 try
4011 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004012 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004013
daniel@transgaming.come0078962010-04-15 20:45:08 +00004014 if (context)
4015 {
4016 if (index >= gl::MAX_VERTEX_ATTRIBS)
4017 {
4018 return error(GL_INVALID_VALUE);
4019 }
4020
daniel@transgaming.com83921382011-01-08 05:46:00 +00004021 const gl::VertexAttribute &attribState = context->getVertexAttribState(index);
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004022
daniel@transgaming.come0078962010-04-15 20:45:08 +00004023 switch (pname)
4024 {
4025 case GL_VERTEX_ATTRIB_ARRAY_ENABLED:
daniel@transgaming.com83921382011-01-08 05:46:00 +00004026 *params = (attribState.mArrayEnabled ? GL_TRUE : GL_FALSE);
daniel@transgaming.come0078962010-04-15 20:45:08 +00004027 break;
4028 case GL_VERTEX_ATTRIB_ARRAY_SIZE:
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004029 *params = attribState.mSize;
daniel@transgaming.come0078962010-04-15 20:45:08 +00004030 break;
4031 case GL_VERTEX_ATTRIB_ARRAY_STRIDE:
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004032 *params = attribState.mStride;
daniel@transgaming.come0078962010-04-15 20:45:08 +00004033 break;
4034 case GL_VERTEX_ATTRIB_ARRAY_TYPE:
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004035 *params = attribState.mType;
daniel@transgaming.come0078962010-04-15 20:45:08 +00004036 break;
4037 case GL_VERTEX_ATTRIB_ARRAY_NORMALIZED:
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004038 *params = (attribState.mNormalized ? GL_TRUE : GL_FALSE);
daniel@transgaming.come0078962010-04-15 20:45:08 +00004039 break;
4040 case GL_VERTEX_ATTRIB_ARRAY_BUFFER_BINDING:
daniel@transgaming.com9ecb9f92010-07-28 19:21:12 +00004041 *params = attribState.mBoundBuffer.id();
daniel@transgaming.come0078962010-04-15 20:45:08 +00004042 break;
4043 case GL_CURRENT_VERTEX_ATTRIB:
4044 for (int i = 0; i < 4; ++i)
4045 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004046 float currentValue = attribState.mCurrentValue[i];
daniel@transgaming.come0078962010-04-15 20:45:08 +00004047 params[i] = (GLint)(currentValue > 0.0f ? floor(currentValue + 0.5f) : ceil(currentValue - 0.5f));
4048 }
4049 break;
daniel@transgaming.comd2820bf2012-01-27 15:38:48 +00004050 case GL_VERTEX_ATTRIB_ARRAY_DIVISOR_ANGLE:
4051 *params = (GLint)attribState.mDivisor;
4052 break;
daniel@transgaming.come0078962010-04-15 20:45:08 +00004053 default: return error(GL_INVALID_ENUM);
4054 }
4055 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004056 }
4057 catch(std::bad_alloc&)
4058 {
4059 return error(GL_OUT_OF_MEMORY);
4060 }
4061}
4062
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00004063void __stdcall glGetVertexAttribPointerv(GLuint index, GLenum pname, GLvoid** pointer)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004064{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004065 EVENT("(GLuint index = %d, GLenum pname = 0x%X, GLvoid** pointer = 0x%0.8p)", index, pname, pointer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004066
4067 try
4068 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004069 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004070
daniel@transgaming.come0078962010-04-15 20:45:08 +00004071 if (context)
4072 {
4073 if (index >= gl::MAX_VERTEX_ATTRIBS)
4074 {
4075 return error(GL_INVALID_VALUE);
4076 }
4077
4078 if (pname != GL_VERTEX_ATTRIB_ARRAY_POINTER)
4079 {
4080 return error(GL_INVALID_ENUM);
4081 }
4082
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004083 *pointer = const_cast<GLvoid*>(context->getVertexAttribPointer(index));
daniel@transgaming.come0078962010-04-15 20:45:08 +00004084 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004085 }
4086 catch(std::bad_alloc&)
4087 {
4088 return error(GL_OUT_OF_MEMORY);
4089 }
4090}
4091
4092void __stdcall glHint(GLenum target, GLenum mode)
4093{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004094 EVENT("(GLenum target = 0x%X, GLenum mode = 0x%X)", target, mode);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004095
4096 try
4097 {
alokp@chromium.orgd303ef92010-09-09 17:30:15 +00004098 switch (mode)
daniel@transgaming.com5949aa12010-03-21 04:31:15 +00004099 {
alokp@chromium.orgd303ef92010-09-09 17:30:15 +00004100 case GL_FASTEST:
4101 case GL_NICEST:
4102 case GL_DONT_CARE:
daniel@transgaming.com5949aa12010-03-21 04:31:15 +00004103 break;
4104 default:
alokp@chromium.orgd303ef92010-09-09 17:30:15 +00004105 return error(GL_INVALID_ENUM);
daniel@transgaming.com5949aa12010-03-21 04:31:15 +00004106 }
4107
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004108 gl::Context *context = gl::getNonLostContext();
alokp@chromium.orgd303ef92010-09-09 17:30:15 +00004109 switch (target)
daniel@transgaming.com5949aa12010-03-21 04:31:15 +00004110 {
alokp@chromium.orgd303ef92010-09-09 17:30:15 +00004111 case GL_GENERATE_MIPMAP_HINT:
4112 if (context) context->setGenerateMipmapHint(mode);
4113 break;
4114 case GL_FRAGMENT_SHADER_DERIVATIVE_HINT_OES:
4115 if (context) context->setFragmentShaderDerivativeHint(mode);
4116 break;
4117 default:
4118 return error(GL_INVALID_ENUM);
daniel@transgaming.com5949aa12010-03-21 04:31:15 +00004119 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004120 }
4121 catch(std::bad_alloc&)
4122 {
4123 return error(GL_OUT_OF_MEMORY);
4124 }
4125}
4126
4127GLboolean __stdcall glIsBuffer(GLuint buffer)
4128{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004129 EVENT("(GLuint buffer = %d)", buffer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004130
4131 try
4132 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004133 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004134
4135 if (context && buffer)
4136 {
4137 gl::Buffer *bufferObject = context->getBuffer(buffer);
4138
4139 if (bufferObject)
4140 {
4141 return GL_TRUE;
4142 }
4143 }
4144 }
4145 catch(std::bad_alloc&)
4146 {
4147 return error(GL_OUT_OF_MEMORY, GL_FALSE);
4148 }
4149
4150 return GL_FALSE;
4151}
4152
4153GLboolean __stdcall glIsEnabled(GLenum cap)
4154{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004155 EVENT("(GLenum cap = 0x%X)", cap);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004156
4157 try
4158 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004159 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004160
4161 if (context)
4162 {
4163 switch (cap)
4164 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004165 case GL_CULL_FACE: return context->isCullFaceEnabled();
4166 case GL_POLYGON_OFFSET_FILL: return context->isPolygonOffsetFillEnabled();
4167 case GL_SAMPLE_ALPHA_TO_COVERAGE: return context->isSampleAlphaToCoverageEnabled();
4168 case GL_SAMPLE_COVERAGE: return context->isSampleCoverageEnabled();
4169 case GL_SCISSOR_TEST: return context->isScissorTestEnabled();
4170 case GL_STENCIL_TEST: return context->isStencilTestEnabled();
4171 case GL_DEPTH_TEST: return context->isDepthTestEnabled();
4172 case GL_BLEND: return context->isBlendEnabled();
4173 case GL_DITHER: return context->isDitherEnabled();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004174 default:
4175 return error(GL_INVALID_ENUM, false);
4176 }
4177 }
4178 }
4179 catch(std::bad_alloc&)
4180 {
4181 return error(GL_OUT_OF_MEMORY, false);
4182 }
4183
4184 return false;
4185}
4186
daniel@transgaming.comfe208882010-09-01 15:47:57 +00004187GLboolean __stdcall glIsFenceNV(GLuint fence)
4188{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004189 EVENT("(GLuint fence = %d)", fence);
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00004190
4191 try
4192 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004193 gl::Context *context = gl::getNonLostContext();
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00004194
4195 if (context)
4196 {
4197 gl::Fence *fenceObject = context->getFence(fence);
4198
4199 if (fenceObject == NULL)
4200 {
4201 return GL_FALSE;
4202 }
4203
4204 return fenceObject->isFence();
4205 }
4206 }
4207 catch(std::bad_alloc&)
4208 {
4209 return error(GL_OUT_OF_MEMORY, GL_FALSE);
4210 }
4211
4212 return GL_FALSE;
daniel@transgaming.comfe208882010-09-01 15:47:57 +00004213}
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00004214
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004215GLboolean __stdcall glIsFramebuffer(GLuint framebuffer)
4216{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004217 EVENT("(GLuint framebuffer = %d)", framebuffer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004218
4219 try
4220 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004221 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004222
4223 if (context && framebuffer)
4224 {
4225 gl::Framebuffer *framebufferObject = context->getFramebuffer(framebuffer);
4226
4227 if (framebufferObject)
4228 {
4229 return GL_TRUE;
4230 }
4231 }
4232 }
4233 catch(std::bad_alloc&)
4234 {
4235 return error(GL_OUT_OF_MEMORY, GL_FALSE);
4236 }
4237
4238 return GL_FALSE;
4239}
4240
4241GLboolean __stdcall glIsProgram(GLuint program)
4242{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004243 EVENT("(GLuint program = %d)", program);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004244
4245 try
4246 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004247 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004248
4249 if (context && program)
4250 {
4251 gl::Program *programObject = context->getProgram(program);
4252
4253 if (programObject)
4254 {
4255 return GL_TRUE;
4256 }
4257 }
4258 }
4259 catch(std::bad_alloc&)
4260 {
4261 return error(GL_OUT_OF_MEMORY, GL_FALSE);
4262 }
4263
4264 return GL_FALSE;
4265}
4266
daniel@transgaming.com86bdb822012-01-20 18:24:39 +00004267GLboolean __stdcall glIsQueryEXT(GLuint id)
4268{
4269 EVENT("(GLuint id = %d)", id);
4270
4271 try
4272 {
4273 if (id == 0)
4274 {
4275 return GL_FALSE;
4276 }
4277
4278 gl::Context *context = gl::getNonLostContext();
4279
4280 if (context)
4281 {
4282 gl::Query *queryObject = context->getQuery(id, false, GL_NONE);
4283
4284 if (queryObject)
4285 {
4286 return GL_TRUE;
4287 }
4288 }
4289 }
4290 catch(std::bad_alloc&)
4291 {
4292 return error(GL_OUT_OF_MEMORY, GL_FALSE);
4293 }
4294
4295 return GL_FALSE;
4296}
4297
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004298GLboolean __stdcall glIsRenderbuffer(GLuint renderbuffer)
4299{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004300 EVENT("(GLuint renderbuffer = %d)", renderbuffer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004301
4302 try
4303 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004304 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004305
4306 if (context && renderbuffer)
4307 {
4308 gl::Renderbuffer *renderbufferObject = context->getRenderbuffer(renderbuffer);
4309
4310 if (renderbufferObject)
4311 {
4312 return GL_TRUE;
4313 }
4314 }
4315 }
4316 catch(std::bad_alloc&)
4317 {
4318 return error(GL_OUT_OF_MEMORY, GL_FALSE);
4319 }
4320
4321 return GL_FALSE;
4322}
4323
4324GLboolean __stdcall glIsShader(GLuint shader)
4325{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004326 EVENT("(GLuint shader = %d)", shader);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004327
4328 try
4329 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004330 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004331
4332 if (context && shader)
4333 {
4334 gl::Shader *shaderObject = context->getShader(shader);
4335
4336 if (shaderObject)
4337 {
4338 return GL_TRUE;
4339 }
4340 }
4341 }
4342 catch(std::bad_alloc&)
4343 {
4344 return error(GL_OUT_OF_MEMORY, GL_FALSE);
4345 }
4346
4347 return GL_FALSE;
4348}
4349
4350GLboolean __stdcall glIsTexture(GLuint texture)
4351{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004352 EVENT("(GLuint texture = %d)", texture);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004353
4354 try
4355 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004356 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004357
4358 if (context && texture)
4359 {
4360 gl::Texture *textureObject = context->getTexture(texture);
4361
4362 if (textureObject)
4363 {
4364 return GL_TRUE;
4365 }
4366 }
4367 }
4368 catch(std::bad_alloc&)
4369 {
4370 return error(GL_OUT_OF_MEMORY, GL_FALSE);
4371 }
4372
4373 return GL_FALSE;
4374}
4375
4376void __stdcall glLineWidth(GLfloat width)
4377{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004378 EVENT("(GLfloat width = %f)", width);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004379
4380 try
4381 {
4382 if (width <= 0.0f)
4383 {
4384 return error(GL_INVALID_VALUE);
4385 }
4386
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004387 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com32e58cd2010-03-24 09:44:10 +00004388
4389 if (context)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004390 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004391 context->setLineWidth(width);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004392 }
4393 }
4394 catch(std::bad_alloc&)
4395 {
4396 return error(GL_OUT_OF_MEMORY);
4397 }
4398}
4399
4400void __stdcall glLinkProgram(GLuint program)
4401{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004402 EVENT("(GLuint program = %d)", program);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004403
4404 try
4405 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004406 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004407
4408 if (context)
4409 {
4410 gl::Program *programObject = context->getProgram(program);
4411
4412 if (!programObject)
4413 {
daniel@transgaming.com277b7142010-04-13 03:26:44 +00004414 if (context->getShader(program))
4415 {
4416 return error(GL_INVALID_OPERATION);
4417 }
4418 else
4419 {
4420 return error(GL_INVALID_VALUE);
4421 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004422 }
4423
4424 programObject->link();
4425 }
4426 }
4427 catch(std::bad_alloc&)
4428 {
4429 return error(GL_OUT_OF_MEMORY);
4430 }
4431}
4432
4433void __stdcall glPixelStorei(GLenum pname, GLint param)
4434{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004435 EVENT("(GLenum pname = 0x%X, GLint param = %d)", pname, param);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004436
4437 try
4438 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004439 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00004440
4441 if (context)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004442 {
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00004443 switch (pname)
4444 {
4445 case GL_UNPACK_ALIGNMENT:
4446 if (param != 1 && param != 2 && param != 4 && param != 8)
4447 {
4448 return error(GL_INVALID_VALUE);
4449 }
4450
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004451 context->setUnpackAlignment(param);
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00004452 break;
4453
4454 case GL_PACK_ALIGNMENT:
4455 if (param != 1 && param != 2 && param != 4 && param != 8)
4456 {
4457 return error(GL_INVALID_VALUE);
4458 }
4459
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004460 context->setPackAlignment(param);
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00004461 break;
4462
bsalomon@google.com56d46ab2011-11-23 14:53:10 +00004463 case GL_PACK_REVERSE_ROW_ORDER_ANGLE:
4464 context->setPackReverseRowOrder(param != 0);
4465 break;
4466
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00004467 default:
4468 return error(GL_INVALID_ENUM);
4469 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004470 }
4471 }
4472 catch(std::bad_alloc&)
4473 {
4474 return error(GL_OUT_OF_MEMORY);
4475 }
4476}
4477
4478void __stdcall glPolygonOffset(GLfloat factor, GLfloat units)
4479{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004480 EVENT("(GLfloat factor = %f, GLfloat units = %f)", factor, units);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004481
4482 try
4483 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004484 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.comaede6302010-04-29 03:35:48 +00004485
4486 if (context)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004487 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004488 context->setPolygonOffsetParams(factor, units);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004489 }
4490 }
4491 catch(std::bad_alloc&)
4492 {
4493 return error(GL_OUT_OF_MEMORY);
4494 }
4495}
4496
daniel@transgaming.comb7915a52011-11-12 03:14:20 +00004497void __stdcall glReadnPixelsEXT(GLint x, GLint y, GLsizei width, GLsizei height,
4498 GLenum format, GLenum type, GLsizei bufSize,
4499 GLvoid *data)
4500{
4501 EVENT("(GLint x = %d, GLint y = %d, GLsizei width = %d, GLsizei height = %d, "
4502 "GLenum format = 0x%X, GLenum type = 0x%X, GLsizei bufSize = 0x%d, GLvoid *data = 0x%0.8p)",
4503 x, y, width, height, format, type, bufSize, data);
4504
4505 try
4506 {
4507 if (width < 0 || height < 0 || bufSize < 0)
4508 {
4509 return error(GL_INVALID_VALUE);
4510 }
4511
4512 if (!validReadFormatType(format, type))
4513 {
4514 return error(GL_INVALID_OPERATION);
4515 }
4516
4517 gl::Context *context = gl::getNonLostContext();
4518
4519 if (context)
4520 {
4521 context->readPixels(x, y, width, height, format, type, &bufSize, data);
4522 }
4523 }
4524 catch(std::bad_alloc&)
4525 {
4526 return error(GL_OUT_OF_MEMORY);
4527 }
4528}
4529
4530void __stdcall glReadPixels(GLint x, GLint y, GLsizei width, GLsizei height,
4531 GLenum format, GLenum type, GLvoid* pixels)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004532{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004533 EVENT("(GLint x = %d, GLint y = %d, GLsizei width = %d, GLsizei height = %d, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00004534 "GLenum format = 0x%X, GLenum type = 0x%X, GLvoid* pixels = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004535 x, y, width, height, format, type, pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004536
4537 try
4538 {
4539 if (width < 0 || height < 0)
4540 {
4541 return error(GL_INVALID_VALUE);
4542 }
4543
daniel@transgaming.comb7915a52011-11-12 03:14:20 +00004544 if (!validReadFormatType(format, type))
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004545 {
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004546 return error(GL_INVALID_OPERATION);
4547 }
4548
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004549 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004550
4551 if (context)
4552 {
daniel@transgaming.comb7915a52011-11-12 03:14:20 +00004553 context->readPixels(x, y, width, height, format, type, NULL, pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004554 }
4555 }
4556 catch(std::bad_alloc&)
4557 {
4558 return error(GL_OUT_OF_MEMORY);
4559 }
4560}
4561
4562void __stdcall glReleaseShaderCompiler(void)
4563{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004564 EVENT("()");
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004565
4566 try
4567 {
4568 gl::Shader::releaseCompiler();
4569 }
4570 catch(std::bad_alloc&)
4571 {
4572 return error(GL_OUT_OF_MEMORY);
4573 }
4574}
4575
daniel@transgaming.com1f135d82010-08-24 19:20:36 +00004576void __stdcall glRenderbufferStorageMultisampleANGLE(GLenum target, GLsizei samples, GLenum internalformat, GLsizei width, GLsizei height)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004577{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004578 EVENT("(GLenum target = 0x%X, GLsizei samples = %d, GLenum internalformat = 0x%X, GLsizei width = %d, GLsizei height = %d)",
daniel@transgaming.com1f135d82010-08-24 19:20:36 +00004579 target, samples, internalformat, width, height);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004580
4581 try
4582 {
4583 switch (target)
4584 {
4585 case GL_RENDERBUFFER:
4586 break;
4587 default:
4588 return error(GL_INVALID_ENUM);
4589 }
4590
daniel@transgaming.comedc19182010-10-15 17:57:55 +00004591 if (!gl::IsColorRenderable(internalformat) && !gl::IsDepthRenderable(internalformat) && !gl::IsStencilRenderable(internalformat))
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004592 {
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004593 return error(GL_INVALID_ENUM);
4594 }
4595
daniel@transgaming.com5d752f22010-10-07 13:37:20 +00004596 if (width < 0 || height < 0 || samples < 0)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004597 {
4598 return error(GL_INVALID_VALUE);
4599 }
4600
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004601 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004602
4603 if (context)
4604 {
daniel@transgaming.com5d752f22010-10-07 13:37:20 +00004605 if (width > context->getMaximumRenderbufferDimension() ||
4606 height > context->getMaximumRenderbufferDimension() ||
4607 samples > context->getMaxSupportedSamples())
daniel@transgaming.com1f135d82010-08-24 19:20:36 +00004608 {
4609 return error(GL_INVALID_VALUE);
4610 }
4611
daniel@transgaming.com9ecb9f92010-07-28 19:21:12 +00004612 GLuint handle = context->getRenderbufferHandle();
4613 if (handle == 0)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004614 {
4615 return error(GL_INVALID_OPERATION);
4616 }
4617
4618 switch (internalformat)
4619 {
4620 case GL_DEPTH_COMPONENT16:
daniel@transgaming.com1f135d82010-08-24 19:20:36 +00004621 context->setRenderbufferStorage(new gl::Depthbuffer(width, height, samples));
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004622 break;
4623 case GL_RGBA4:
4624 case GL_RGB5_A1:
4625 case GL_RGB565:
daniel@transgaming.com63977542010-08-24 19:21:02 +00004626 case GL_RGB8_OES:
4627 case GL_RGBA8_OES:
daniel@transgaming.com1f135d82010-08-24 19:20:36 +00004628 context->setRenderbufferStorage(new gl::Colorbuffer(width, height, internalformat, samples));
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004629 break;
4630 case GL_STENCIL_INDEX8:
daniel@transgaming.com1f135d82010-08-24 19:20:36 +00004631 context->setRenderbufferStorage(new gl::Stencilbuffer(width, height, samples));
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004632 break;
daniel@transgaming.comcdacc8e2010-07-28 19:20:50 +00004633 case GL_DEPTH24_STENCIL8_OES:
daniel@transgaming.com1f135d82010-08-24 19:20:36 +00004634 context->setRenderbufferStorage(new gl::DepthStencilbuffer(width, height, samples));
daniel@transgaming.comcdacc8e2010-07-28 19:20:50 +00004635 break;
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004636 default:
4637 return error(GL_INVALID_ENUM);
4638 }
4639 }
4640 }
4641 catch(std::bad_alloc&)
4642 {
4643 return error(GL_OUT_OF_MEMORY);
4644 }
4645}
4646
daniel@transgaming.com1f135d82010-08-24 19:20:36 +00004647void __stdcall glRenderbufferStorage(GLenum target, GLenum internalformat, GLsizei width, GLsizei height)
4648{
4649 glRenderbufferStorageMultisampleANGLE(target, 0, internalformat, width, height);
4650}
4651
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004652void __stdcall glSampleCoverage(GLclampf value, GLboolean invert)
4653{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004654 EVENT("(GLclampf value = %f, GLboolean invert = %d)", value, invert);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004655
4656 try
4657 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004658 gl::Context* context = gl::getNonLostContext();
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00004659
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004660 if (context)
4661 {
daniel@transgaming.coma36f98e2010-05-18 18:51:09 +00004662 context->setSampleCoverageParams(gl::clamp01(value), invert == GL_TRUE);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004663 }
4664 }
4665 catch(std::bad_alloc&)
4666 {
4667 return error(GL_OUT_OF_MEMORY);
4668 }
4669}
4670
daniel@transgaming.comfe208882010-09-01 15:47:57 +00004671void __stdcall glSetFenceNV(GLuint fence, GLenum condition)
4672{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004673 EVENT("(GLuint fence = %d, GLenum condition = 0x%X)", fence, condition);
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00004674
4675 try
4676 {
4677 if (condition != GL_ALL_COMPLETED_NV)
4678 {
4679 return error(GL_INVALID_ENUM);
4680 }
4681
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004682 gl::Context *context = gl::getNonLostContext();
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00004683
4684 if (context)
4685 {
4686 gl::Fence *fenceObject = context->getFence(fence);
4687
4688 if (fenceObject == NULL)
4689 {
4690 return error(GL_INVALID_OPERATION);
4691 }
4692
4693 fenceObject->setFence(condition);
4694 }
4695 }
4696 catch(std::bad_alloc&)
4697 {
4698 return error(GL_OUT_OF_MEMORY);
4699 }
daniel@transgaming.comfe208882010-09-01 15:47:57 +00004700}
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00004701
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004702void __stdcall glScissor(GLint x, GLint y, GLsizei width, GLsizei height)
4703{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004704 EVENT("(GLint x = %d, GLint y = %d, GLsizei width = %d, GLsizei height = %d)", x, y, width, height);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004705
4706 try
4707 {
4708 if (width < 0 || height < 0)
4709 {
4710 return error(GL_INVALID_VALUE);
4711 }
4712
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004713 gl::Context* context = gl::getNonLostContext();
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00004714
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004715 if (context)
4716 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004717 context->setScissorParams(x, y, width, height);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004718 }
4719 }
4720 catch(std::bad_alloc&)
4721 {
4722 return error(GL_OUT_OF_MEMORY);
4723 }
4724}
4725
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00004726void __stdcall glShaderBinary(GLsizei n, const GLuint* shaders, GLenum binaryformat, const GLvoid* binary, GLsizei length)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004727{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004728 EVENT("(GLsizei n = %d, const GLuint* shaders = 0x%0.8p, GLenum binaryformat = 0x%X, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00004729 "const GLvoid* binary = 0x%0.8p, GLsizei length = %d)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004730 n, shaders, binaryformat, binary, length);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004731
4732 try
4733 {
daniel@transgaming.comd1f667f2010-04-29 03:38:52 +00004734 // No binary shader formats are supported.
4735 return error(GL_INVALID_ENUM);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004736 }
4737 catch(std::bad_alloc&)
4738 {
4739 return error(GL_OUT_OF_MEMORY);
4740 }
4741}
4742
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00004743void __stdcall glShaderSource(GLuint shader, GLsizei count, const GLchar** string, const GLint* length)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004744{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004745 EVENT("(GLuint shader = %d, GLsizei count = %d, const GLchar** string = 0x%0.8p, const GLint* length = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004746 shader, count, string, length);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004747
4748 try
4749 {
daniel@transgaming.com8e6a6be2010-04-13 03:26:41 +00004750 if (count < 0)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004751 {
4752 return error(GL_INVALID_VALUE);
4753 }
4754
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004755 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004756
4757 if (context)
4758 {
4759 gl::Shader *shaderObject = context->getShader(shader);
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00004760
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004761 if (!shaderObject)
4762 {
daniel@transgaming.com8e6a6be2010-04-13 03:26:41 +00004763 if (context->getProgram(shader))
4764 {
4765 return error(GL_INVALID_OPERATION);
4766 }
4767 else
4768 {
4769 return error(GL_INVALID_VALUE);
4770 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004771 }
4772
4773 shaderObject->setSource(count, string, length);
4774 }
4775 }
4776 catch(std::bad_alloc&)
4777 {
4778 return error(GL_OUT_OF_MEMORY);
4779 }
4780}
4781
4782void __stdcall glStencilFunc(GLenum func, GLint ref, GLuint mask)
4783{
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00004784 glStencilFuncSeparate(GL_FRONT_AND_BACK, func, ref, mask);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004785}
4786
4787void __stdcall glStencilFuncSeparate(GLenum face, GLenum func, GLint ref, GLuint mask)
4788{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004789 EVENT("(GLenum face = 0x%X, GLenum func = 0x%X, GLint ref = %d, GLuint mask = %d)", face, func, ref, mask);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004790
4791 try
4792 {
4793 switch (face)
4794 {
4795 case GL_FRONT:
4796 case GL_BACK:
4797 case GL_FRONT_AND_BACK:
4798 break;
4799 default:
4800 return error(GL_INVALID_ENUM);
4801 }
4802
4803 switch (func)
4804 {
4805 case GL_NEVER:
4806 case GL_ALWAYS:
4807 case GL_LESS:
4808 case GL_LEQUAL:
4809 case GL_EQUAL:
4810 case GL_GEQUAL:
4811 case GL_GREATER:
4812 case GL_NOTEQUAL:
4813 break;
4814 default:
4815 return error(GL_INVALID_ENUM);
4816 }
4817
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004818 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004819
4820 if (context)
4821 {
4822 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
4823 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004824 context->setStencilParams(func, ref, mask);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004825 }
4826
4827 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
4828 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004829 context->setStencilBackParams(func, ref, mask);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004830 }
4831 }
4832 }
4833 catch(std::bad_alloc&)
4834 {
4835 return error(GL_OUT_OF_MEMORY);
4836 }
4837}
4838
4839void __stdcall glStencilMask(GLuint mask)
4840{
4841 glStencilMaskSeparate(GL_FRONT_AND_BACK, mask);
4842}
4843
4844void __stdcall glStencilMaskSeparate(GLenum face, GLuint mask)
4845{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004846 EVENT("(GLenum face = 0x%X, GLuint mask = %d)", face, mask);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004847
4848 try
4849 {
4850 switch (face)
4851 {
4852 case GL_FRONT:
4853 case GL_BACK:
4854 case GL_FRONT_AND_BACK:
4855 break;
4856 default:
4857 return error(GL_INVALID_ENUM);
4858 }
4859
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004860 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004861
4862 if (context)
4863 {
4864 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
4865 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004866 context->setStencilWritemask(mask);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004867 }
4868
4869 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
4870 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004871 context->setStencilBackWritemask(mask);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004872 }
4873 }
4874 }
4875 catch(std::bad_alloc&)
4876 {
4877 return error(GL_OUT_OF_MEMORY);
4878 }
4879}
4880
4881void __stdcall glStencilOp(GLenum fail, GLenum zfail, GLenum zpass)
4882{
4883 glStencilOpSeparate(GL_FRONT_AND_BACK, fail, zfail, zpass);
4884}
4885
4886void __stdcall glStencilOpSeparate(GLenum face, GLenum fail, GLenum zfail, GLenum zpass)
4887{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004888 EVENT("(GLenum face = 0x%X, GLenum fail = 0x%X, GLenum zfail = 0x%X, GLenum zpas = 0x%Xs)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004889 face, fail, zfail, zpass);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004890
4891 try
4892 {
4893 switch (face)
4894 {
4895 case GL_FRONT:
4896 case GL_BACK:
4897 case GL_FRONT_AND_BACK:
4898 break;
4899 default:
4900 return error(GL_INVALID_ENUM);
4901 }
4902
4903 switch (fail)
4904 {
4905 case GL_ZERO:
4906 case GL_KEEP:
4907 case GL_REPLACE:
4908 case GL_INCR:
4909 case GL_DECR:
4910 case GL_INVERT:
4911 case GL_INCR_WRAP:
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00004912 case GL_DECR_WRAP:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004913 break;
4914 default:
4915 return error(GL_INVALID_ENUM);
4916 }
4917
4918 switch (zfail)
4919 {
4920 case GL_ZERO:
4921 case GL_KEEP:
4922 case GL_REPLACE:
4923 case GL_INCR:
4924 case GL_DECR:
4925 case GL_INVERT:
4926 case GL_INCR_WRAP:
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00004927 case GL_DECR_WRAP:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004928 break;
4929 default:
4930 return error(GL_INVALID_ENUM);
4931 }
4932
4933 switch (zpass)
4934 {
4935 case GL_ZERO:
4936 case GL_KEEP:
4937 case GL_REPLACE:
4938 case GL_INCR:
4939 case GL_DECR:
4940 case GL_INVERT:
4941 case GL_INCR_WRAP:
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00004942 case GL_DECR_WRAP:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004943 break;
4944 default:
4945 return error(GL_INVALID_ENUM);
4946 }
4947
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004948 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004949
4950 if (context)
4951 {
4952 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
4953 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004954 context->setStencilOperations(fail, zfail, zpass);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004955 }
4956
4957 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
4958 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00004959 context->setStencilBackOperations(fail, zfail, zpass);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004960 }
4961 }
4962 }
4963 catch(std::bad_alloc&)
4964 {
4965 return error(GL_OUT_OF_MEMORY);
4966 }
4967}
4968
daniel@transgaming.comfe208882010-09-01 15:47:57 +00004969GLboolean __stdcall glTestFenceNV(GLuint fence)
4970{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00004971 EVENT("(GLuint fence = %d)", fence);
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00004972
4973 try
4974 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00004975 gl::Context *context = gl::getNonLostContext();
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00004976
4977 if (context)
4978 {
4979 gl::Fence *fenceObject = context->getFence(fence);
4980
4981 if (fenceObject == NULL)
4982 {
4983 return error(GL_INVALID_OPERATION, GL_TRUE);
4984 }
4985
4986 return fenceObject->testFence();
4987 }
4988 }
4989 catch(std::bad_alloc&)
4990 {
4991 error(GL_OUT_OF_MEMORY);
4992 }
4993
4994 return GL_TRUE;
daniel@transgaming.comfe208882010-09-01 15:47:57 +00004995}
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00004996
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00004997void __stdcall glTexImage2D(GLenum target, GLint level, GLint internalformat, GLsizei width, GLsizei height,
4998 GLint border, GLenum format, GLenum type, const GLvoid* pixels)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004999{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00005000 EVENT("(GLenum target = 0x%X, GLint level = %d, GLint internalformat = %d, GLsizei width = %d, GLsizei height = %d, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00005001 "GLint border = %d, GLenum format = 0x%X, GLenum type = 0x%X, const GLvoid* pixels = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00005002 target, level, internalformat, width, height, border, format, type, pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005003
5004 try
5005 {
daniel@transgaming.com4f9ef0d2011-05-30 23:51:19 +00005006 if (!validImageSize(level, width, height))
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005007 {
5008 return error(GL_INVALID_VALUE);
5009 }
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00005010
apatrick@chromium.orge057c5d2012-01-26 19:18:24 +00005011 if (internalformat != GLint(format))
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005012 {
5013 return error(GL_INVALID_OPERATION);
5014 }
5015
daniel@transgaming.com8a0a2db2011-03-21 16:38:20 +00005016 switch (format)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005017 {
5018 case GL_ALPHA:
5019 case GL_LUMINANCE:
5020 case GL_LUMINANCE_ALPHA:
5021 switch (type)
5022 {
5023 case GL_UNSIGNED_BYTE:
daniel@transgaming.com0a337e92010-08-28 17:38:27 +00005024 case GL_FLOAT:
5025 case GL_HALF_FLOAT_OES:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005026 break;
5027 default:
5028 return error(GL_INVALID_ENUM);
5029 }
5030 break;
5031 case GL_RGB:
5032 switch (type)
5033 {
5034 case GL_UNSIGNED_BYTE:
5035 case GL_UNSIGNED_SHORT_5_6_5:
daniel@transgaming.com0a337e92010-08-28 17:38:27 +00005036 case GL_FLOAT:
5037 case GL_HALF_FLOAT_OES:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005038 break;
5039 default:
5040 return error(GL_INVALID_ENUM);
5041 }
5042 break;
5043 case GL_RGBA:
5044 switch (type)
5045 {
5046 case GL_UNSIGNED_BYTE:
5047 case GL_UNSIGNED_SHORT_4_4_4_4:
5048 case GL_UNSIGNED_SHORT_5_5_5_1:
daniel@transgaming.com0a337e92010-08-28 17:38:27 +00005049 case GL_FLOAT:
5050 case GL_HALF_FLOAT_OES:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005051 break;
5052 default:
5053 return error(GL_INVALID_ENUM);
5054 }
5055 break;
daniel@transgaming.coma9198d92010-08-08 04:49:56 +00005056 case GL_BGRA_EXT:
5057 switch (type)
5058 {
5059 case GL_UNSIGNED_BYTE:
5060 break;
5061 default:
5062 return error(GL_INVALID_ENUM);
5063 }
5064 break;
daniel@transgaming.com01868132010-08-24 19:21:17 +00005065 case GL_COMPRESSED_RGB_S3TC_DXT1_EXT: // error cases for compressed textures are handled below
5066 case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
gman@chromium.org50c526d2011-08-10 05:19:44 +00005067 case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
5068 case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
daniel@transgaming.com01868132010-08-24 19:21:17 +00005069 break;
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005070 default:
5071 return error(GL_INVALID_VALUE);
5072 }
5073
5074 if (border != 0)
5075 {
5076 return error(GL_INVALID_VALUE);
5077 }
5078
daniel@transgaming.com9d788502011-11-09 17:46:55 +00005079 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005080
5081 if (context)
5082 {
daniel@transgaming.com32b11442011-11-19 02:42:48 +00005083 if (level > context->getMaximumTextureLevel())
5084 {
5085 return error(GL_INVALID_VALUE);
5086 }
5087
daniel@transgaming.com5d752f22010-10-07 13:37:20 +00005088 switch (target)
5089 {
5090 case GL_TEXTURE_2D:
5091 if (width > (context->getMaximumTextureDimension() >> level) ||
5092 height > (context->getMaximumTextureDimension() >> level))
5093 {
5094 return error(GL_INVALID_VALUE);
5095 }
5096 break;
5097 case GL_TEXTURE_CUBE_MAP_POSITIVE_X:
5098 case GL_TEXTURE_CUBE_MAP_NEGATIVE_X:
5099 case GL_TEXTURE_CUBE_MAP_POSITIVE_Y:
5100 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y:
5101 case GL_TEXTURE_CUBE_MAP_POSITIVE_Z:
5102 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z:
5103 if (width != height)
5104 {
5105 return error(GL_INVALID_VALUE);
5106 }
5107
5108 if (width > (context->getMaximumCubeTextureDimension() >> level) ||
5109 height > (context->getMaximumCubeTextureDimension() >> level))
5110 {
5111 return error(GL_INVALID_VALUE);
5112 }
5113 break;
5114 default:
5115 return error(GL_INVALID_ENUM);
5116 }
5117
gman@chromium.org50c526d2011-08-10 05:19:44 +00005118 switch (format) {
5119 case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
5120 case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
5121 if (context->supportsDXT1Textures())
daniel@transgaming.com01868132010-08-24 19:21:17 +00005122 {
5123 return error(GL_INVALID_OPERATION);
5124 }
5125 else
5126 {
5127 return error(GL_INVALID_ENUM);
5128 }
gman@chromium.org50c526d2011-08-10 05:19:44 +00005129 break;
5130 case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
5131 if (context->supportsDXT3Textures())
5132 {
5133 return error(GL_INVALID_OPERATION);
5134 }
5135 else
5136 {
5137 return error(GL_INVALID_ENUM);
5138 }
5139 break;
5140 case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
5141 if (context->supportsDXT5Textures())
5142 {
5143 return error(GL_INVALID_OPERATION);
5144 }
5145 else
5146 {
5147 return error(GL_INVALID_ENUM);
5148 }
5149 break;
5150 default:
5151 break;
daniel@transgaming.com01868132010-08-24 19:21:17 +00005152 }
5153
daniel@transgaming.com0a337e92010-08-28 17:38:27 +00005154 if (type == GL_FLOAT)
5155 {
daniel@transgaming.combbeffbb2011-11-09 17:46:11 +00005156 if (!context->supportsFloat32Textures())
daniel@transgaming.com0a337e92010-08-28 17:38:27 +00005157 {
5158 return error(GL_INVALID_ENUM);
5159 }
5160 }
5161 else if (type == GL_HALF_FLOAT_OES)
5162 {
daniel@transgaming.combbeffbb2011-11-09 17:46:11 +00005163 if (!context->supportsFloat16Textures())
daniel@transgaming.com0a337e92010-08-28 17:38:27 +00005164 {
5165 return error(GL_INVALID_ENUM);
5166 }
5167 }
5168
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005169 if (target == GL_TEXTURE_2D)
5170 {
5171 gl::Texture2D *texture = context->getTexture2D();
5172
5173 if (!texture)
5174 {
5175 return error(GL_INVALID_OPERATION);
5176 }
5177
daniel@transgaming.com64a0fb22011-11-11 04:10:40 +00005178 if (texture->isImmutable())
5179 {
5180 return error(GL_INVALID_OPERATION);
5181 }
5182
daniel@transgaming.com8a0a2db2011-03-21 16:38:20 +00005183 texture->setImage(level, width, height, format, type, context->getUnpackAlignment(), pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005184 }
5185 else
5186 {
5187 gl::TextureCubeMap *texture = context->getTextureCubeMap();
5188
5189 if (!texture)
5190 {
5191 return error(GL_INVALID_OPERATION);
5192 }
5193
daniel@transgaming.com64a0fb22011-11-11 04:10:40 +00005194 if (texture->isImmutable())
5195 {
5196 return error(GL_INVALID_OPERATION);
5197 }
5198
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005199 switch (target)
5200 {
5201 case GL_TEXTURE_CUBE_MAP_POSITIVE_X:
daniel@transgaming.com8a0a2db2011-03-21 16:38:20 +00005202 texture->setImagePosX(level, width, height, format, type, context->getUnpackAlignment(), pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005203 break;
5204 case GL_TEXTURE_CUBE_MAP_NEGATIVE_X:
daniel@transgaming.com8a0a2db2011-03-21 16:38:20 +00005205 texture->setImageNegX(level, width, height, format, type, context->getUnpackAlignment(), pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005206 break;
5207 case GL_TEXTURE_CUBE_MAP_POSITIVE_Y:
daniel@transgaming.com8a0a2db2011-03-21 16:38:20 +00005208 texture->setImagePosY(level, width, height, format, type, context->getUnpackAlignment(), pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005209 break;
5210 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y:
daniel@transgaming.com8a0a2db2011-03-21 16:38:20 +00005211 texture->setImageNegY(level, width, height, format, type, context->getUnpackAlignment(), pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005212 break;
5213 case GL_TEXTURE_CUBE_MAP_POSITIVE_Z:
daniel@transgaming.com8a0a2db2011-03-21 16:38:20 +00005214 texture->setImagePosZ(level, width, height, format, type, context->getUnpackAlignment(), pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005215 break;
5216 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z:
daniel@transgaming.com8a0a2db2011-03-21 16:38:20 +00005217 texture->setImageNegZ(level, width, height, format, type, context->getUnpackAlignment(), pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005218 break;
5219 default: UNREACHABLE();
5220 }
5221 }
5222 }
5223 }
5224 catch(std::bad_alloc&)
5225 {
5226 return error(GL_OUT_OF_MEMORY);
5227 }
5228}
5229
5230void __stdcall glTexParameterf(GLenum target, GLenum pname, GLfloat param)
5231{
5232 glTexParameteri(target, pname, (GLint)param);
5233}
5234
5235void __stdcall glTexParameterfv(GLenum target, GLenum pname, const GLfloat* params)
5236{
5237 glTexParameteri(target, pname, (GLint)*params);
5238}
5239
5240void __stdcall glTexParameteri(GLenum target, GLenum pname, GLint param)
5241{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00005242 EVENT("(GLenum target = 0x%X, GLenum pname = 0x%X, GLint param = %d)", target, pname, param);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005243
5244 try
5245 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00005246 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005247
5248 if (context)
5249 {
5250 gl::Texture *texture;
5251
5252 switch (target)
5253 {
5254 case GL_TEXTURE_2D:
5255 texture = context->getTexture2D();
5256 break;
5257 case GL_TEXTURE_CUBE_MAP:
5258 texture = context->getTextureCubeMap();
5259 break;
5260 default:
5261 return error(GL_INVALID_ENUM);
5262 }
5263
5264 switch (pname)
5265 {
5266 case GL_TEXTURE_WRAP_S:
5267 if (!texture->setWrapS((GLenum)param))
5268 {
5269 return error(GL_INVALID_ENUM);
5270 }
5271 break;
5272 case GL_TEXTURE_WRAP_T:
5273 if (!texture->setWrapT((GLenum)param))
5274 {
5275 return error(GL_INVALID_ENUM);
5276 }
5277 break;
5278 case GL_TEXTURE_MIN_FILTER:
5279 if (!texture->setMinFilter((GLenum)param))
5280 {
5281 return error(GL_INVALID_ENUM);
5282 }
5283 break;
5284 case GL_TEXTURE_MAG_FILTER:
5285 if (!texture->setMagFilter((GLenum)param))
5286 {
5287 return error(GL_INVALID_ENUM);
5288 }
5289 break;
daniel@transgaming.com7d18c172011-11-11 04:18:21 +00005290 case GL_TEXTURE_USAGE_ANGLE:
5291 if (!texture->setUsage((GLenum)param))
5292 {
5293 return error(GL_INVALID_ENUM);
5294 }
5295 break;
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005296 default:
5297 return error(GL_INVALID_ENUM);
5298 }
5299 }
5300 }
5301 catch(std::bad_alloc&)
5302 {
5303 return error(GL_OUT_OF_MEMORY);
5304 }
5305}
5306
5307void __stdcall glTexParameteriv(GLenum target, GLenum pname, const GLint* params)
5308{
5309 glTexParameteri(target, pname, *params);
5310}
5311
daniel@transgaming.com64a0fb22011-11-11 04:10:40 +00005312void __stdcall glTexStorage2DEXT(GLenum target, GLsizei levels, GLenum internalformat, GLsizei width, GLsizei height)
5313{
5314 EVENT("(GLenum target = 0x%X, GLsizei levels = %d, GLenum internalformat = 0x%X, GLsizei width = %d, GLsizei height = %d)",
5315 target, levels, internalformat, width, height);
5316
5317 try
5318 {
5319 if (target != GL_TEXTURE_2D && target != GL_TEXTURE_CUBE_MAP)
5320 {
5321 return error(GL_INVALID_ENUM);
5322 }
5323
5324 if (width < 1 || height < 1 || levels < 1)
5325 {
5326 return error(GL_INVALID_VALUE);
5327 }
5328
5329 if (target == GL_TEXTURE_CUBE_MAP && width != height)
5330 {
5331 return error(GL_INVALID_VALUE);
5332 }
5333
daniel@transgaming.com45b888a2011-11-16 03:56:39 +00005334 if (levels != 1 && levels != gl::log2(std::max(width, height)) + 1)
daniel@transgaming.com64a0fb22011-11-11 04:10:40 +00005335 {
5336 return error(GL_INVALID_OPERATION);
5337 }
5338
5339 GLenum format = gl::ExtractFormat(internalformat);
5340 GLenum type = gl::ExtractType(internalformat);
5341
5342 if (format == GL_NONE || type == GL_NONE)
5343 {
5344 return error(GL_INVALID_ENUM);
5345 }
5346
5347 gl::Context *context = gl::getNonLostContext();
5348
5349 if (context)
5350 {
daniel@transgaming.com21f05d72011-11-29 19:42:28 +00005351 switch (target)
5352 {
5353 case GL_TEXTURE_2D:
5354 if (width > context->getMaximumTextureDimension() ||
5355 height > context->getMaximumTextureDimension())
5356 {
5357 return error(GL_INVALID_VALUE);
5358 }
5359 break;
5360 case GL_TEXTURE_CUBE_MAP:
5361 if (width > context->getMaximumCubeTextureDimension() ||
5362 height > context->getMaximumCubeTextureDimension())
5363 {
5364 return error(GL_INVALID_VALUE);
5365 }
5366 break;
5367 default:
5368 return error(GL_INVALID_ENUM);
5369 }
5370
daniel@transgaming.com64a0fb22011-11-11 04:10:40 +00005371 if (levels != 1 && !context->supportsNonPower2Texture())
5372 {
5373 if (!gl::isPow2(width) || !gl::isPow2(height))
5374 {
5375 return error(GL_INVALID_OPERATION);
5376 }
5377 }
5378
daniel@transgaming.come1077362011-11-11 04:16:50 +00005379 switch (internalformat)
5380 {
5381 case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
5382 case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
5383 if (!context->supportsDXT1Textures())
5384 {
5385 return error(GL_INVALID_ENUM);
5386 }
5387 break;
5388 case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
5389 if (!context->supportsDXT3Textures())
5390 {
5391 return error(GL_INVALID_ENUM);
5392 }
5393 break;
5394 case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
5395 if (!context->supportsDXT5Textures())
5396 {
5397 return error(GL_INVALID_ENUM);
5398 }
5399 break;
daniel@transgaming.comff941aa2011-11-11 04:17:09 +00005400 case GL_RGBA32F_EXT:
5401 case GL_RGB32F_EXT:
5402 case GL_ALPHA32F_EXT:
5403 case GL_LUMINANCE32F_EXT:
5404 case GL_LUMINANCE_ALPHA32F_EXT:
5405 if (!context->supportsFloat32Textures())
5406 {
5407 return error(GL_INVALID_ENUM);
5408 }
5409 break;
5410 case GL_RGBA16F_EXT:
5411 case GL_RGB16F_EXT:
5412 case GL_ALPHA16F_EXT:
5413 case GL_LUMINANCE16F_EXT:
5414 case GL_LUMINANCE_ALPHA16F_EXT:
5415 if (!context->supportsFloat16Textures())
5416 {
5417 return error(GL_INVALID_ENUM);
5418 }
5419 break;
daniel@transgaming.come1077362011-11-11 04:16:50 +00005420 }
5421
daniel@transgaming.com64a0fb22011-11-11 04:10:40 +00005422 if (target == GL_TEXTURE_2D)
5423 {
5424 gl::Texture2D *texture = context->getTexture2D();
5425
5426 if (!texture || texture->id() == 0)
5427 {
5428 return error(GL_INVALID_OPERATION);
5429 }
5430
5431 if (texture->isImmutable())
5432 {
5433 return error(GL_INVALID_OPERATION);
5434 }
5435
5436 texture->storage(levels, internalformat, width, height);
5437 }
5438 else if (target == GL_TEXTURE_CUBE_MAP)
5439 {
5440 gl::TextureCubeMap *texture = context->getTextureCubeMap();
5441
5442 if (!texture || texture->id() == 0)
5443 {
5444 return error(GL_INVALID_OPERATION);
5445 }
5446
5447 if (texture->isImmutable())
5448 {
5449 return error(GL_INVALID_OPERATION);
5450 }
5451
5452 texture->storage(levels, internalformat, width);
5453 }
5454 else UNREACHABLE();
5455 }
5456 }
5457 catch(std::bad_alloc&)
5458 {
5459 return error(GL_OUT_OF_MEMORY);
5460 }
5461}
5462
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00005463void __stdcall glTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
5464 GLenum format, GLenum type, const GLvoid* pixels)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005465{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00005466 EVENT("(GLenum target = 0x%X, GLint level = %d, GLint xoffset = %d, GLint yoffset = %d, "
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00005467 "GLsizei width = %d, GLsizei height = %d, GLenum format = 0x%X, GLenum type = 0x%X, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00005468 "const GLvoid* pixels = 0x%0.8p)",
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005469 target, level, xoffset, yoffset, width, height, format, type, pixels);
5470
5471 try
5472 {
apatrick@chromium.org551022e2012-01-23 19:56:54 +00005473 if (!gl::IsInternalTextureTarget(target))
daniel@transgaming.com00c75962010-03-11 20:36:15 +00005474 {
5475 return error(GL_INVALID_ENUM);
5476 }
5477
daniel@transgaming.com5d752f22010-10-07 13:37:20 +00005478 if (level < 0 || xoffset < 0 || yoffset < 0 || width < 0 || height < 0)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005479 {
5480 return error(GL_INVALID_VALUE);
5481 }
5482
daniel@transgaming.com00c75962010-03-11 20:36:15 +00005483 if (std::numeric_limits<GLsizei>::max() - xoffset < width || std::numeric_limits<GLsizei>::max() - yoffset < height)
5484 {
5485 return error(GL_INVALID_VALUE);
5486 }
5487
daniel@transgaming.com19ffc242010-05-04 03:35:21 +00005488 if (!gl::CheckTextureFormatType(format, type))
daniel@transgaming.com00c75962010-03-11 20:36:15 +00005489 {
5490 return error(GL_INVALID_ENUM);
5491 }
5492
5493 if (width == 0 || height == 0 || pixels == NULL)
5494 {
5495 return;
5496 }
5497
daniel@transgaming.com9d788502011-11-09 17:46:55 +00005498 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com00c75962010-03-11 20:36:15 +00005499
5500 if (context)
5501 {
daniel@transgaming.com5d752f22010-10-07 13:37:20 +00005502 if (level > context->getMaximumTextureLevel())
5503 {
5504 return error(GL_INVALID_VALUE);
5505 }
5506
daniel@transgaming.com0a337e92010-08-28 17:38:27 +00005507 if (format == GL_FLOAT)
5508 {
daniel@transgaming.combbeffbb2011-11-09 17:46:11 +00005509 if (!context->supportsFloat32Textures())
daniel@transgaming.com0a337e92010-08-28 17:38:27 +00005510 {
5511 return error(GL_INVALID_ENUM);
5512 }
5513 }
5514 else if (format == GL_HALF_FLOAT_OES)
5515 {
daniel@transgaming.combbeffbb2011-11-09 17:46:11 +00005516 if (!context->supportsFloat16Textures())
daniel@transgaming.com0a337e92010-08-28 17:38:27 +00005517 {
5518 return error(GL_INVALID_ENUM);
5519 }
5520 }
5521
daniel@transgaming.com00c75962010-03-11 20:36:15 +00005522 if (target == GL_TEXTURE_2D)
5523 {
5524 gl::Texture2D *texture = context->getTexture2D();
daniel@transgaming.com343373a2011-11-29 19:42:32 +00005525 if (validateSubImageParams(false, width, height, xoffset, yoffset, level, format, texture))
daniel@transgaming.com00c75962010-03-11 20:36:15 +00005526 {
daniel@transgaming.com343373a2011-11-29 19:42:32 +00005527 texture->subImage(level, xoffset, yoffset, width, height, format, type, context->getUnpackAlignment(), pixels);
daniel@transgaming.com00c75962010-03-11 20:36:15 +00005528 }
daniel@transgaming.com00c75962010-03-11 20:36:15 +00005529 }
daniel@transgaming.com19ffc242010-05-04 03:35:21 +00005530 else if (gl::IsCubemapTextureTarget(target))
daniel@transgaming.com00c75962010-03-11 20:36:15 +00005531 {
5532 gl::TextureCubeMap *texture = context->getTextureCubeMap();
daniel@transgaming.com343373a2011-11-29 19:42:32 +00005533 if (validateSubImageParams(false, width, height, xoffset, yoffset, level, format, texture))
daniel@transgaming.com00c75962010-03-11 20:36:15 +00005534 {
daniel@transgaming.com343373a2011-11-29 19:42:32 +00005535 texture->subImage(target, level, xoffset, yoffset, width, height, format, type, context->getUnpackAlignment(), pixels);
daniel@transgaming.com00c75962010-03-11 20:36:15 +00005536 }
daniel@transgaming.com00c75962010-03-11 20:36:15 +00005537 }
5538 else
5539 {
5540 UNREACHABLE();
5541 }
5542 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005543 }
5544 catch(std::bad_alloc&)
5545 {
5546 return error(GL_OUT_OF_MEMORY);
5547 }
5548}
5549
5550void __stdcall glUniform1f(GLint location, GLfloat x)
5551{
5552 glUniform1fv(location, 1, &x);
5553}
5554
5555void __stdcall glUniform1fv(GLint location, GLsizei count, const GLfloat* v)
5556{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00005557 EVENT("(GLint location = %d, GLsizei count = %d, const GLfloat* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005558
5559 try
5560 {
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005561 if (count < 0)
5562 {
5563 return error(GL_INVALID_VALUE);
5564 }
5565
daniel@transgaming.com9a95e2b2010-04-13 03:26:03 +00005566 if (location == -1)
5567 {
5568 return;
5569 }
5570
daniel@transgaming.com9d788502011-11-09 17:46:55 +00005571 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005572
5573 if (context)
5574 {
5575 gl::Program *program = context->getCurrentProgram();
5576
5577 if (!program)
5578 {
5579 return error(GL_INVALID_OPERATION);
5580 }
5581
5582 if (!program->setUniform1fv(location, count, v))
5583 {
5584 return error(GL_INVALID_OPERATION);
5585 }
5586 }
5587 }
5588 catch(std::bad_alloc&)
5589 {
5590 return error(GL_OUT_OF_MEMORY);
5591 }
5592}
5593
5594void __stdcall glUniform1i(GLint location, GLint x)
5595{
5596 glUniform1iv(location, 1, &x);
5597}
5598
5599void __stdcall glUniform1iv(GLint location, GLsizei count, const GLint* v)
5600{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00005601 EVENT("(GLint location = %d, GLsizei count = %d, const GLint* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005602
5603 try
5604 {
5605 if (count < 0)
5606 {
5607 return error(GL_INVALID_VALUE);
5608 }
5609
daniel@transgaming.com9a95e2b2010-04-13 03:26:03 +00005610 if (location == -1)
5611 {
5612 return;
5613 }
5614
daniel@transgaming.com9d788502011-11-09 17:46:55 +00005615 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005616
5617 if (context)
5618 {
5619 gl::Program *program = context->getCurrentProgram();
5620
5621 if (!program)
5622 {
5623 return error(GL_INVALID_OPERATION);
5624 }
5625
5626 if (!program->setUniform1iv(location, count, v))
5627 {
5628 return error(GL_INVALID_OPERATION);
5629 }
5630 }
5631 }
5632 catch(std::bad_alloc&)
5633 {
5634 return error(GL_OUT_OF_MEMORY);
5635 }
5636}
5637
5638void __stdcall glUniform2f(GLint location, GLfloat x, GLfloat y)
5639{
5640 GLfloat xy[2] = {x, y};
5641
5642 glUniform2fv(location, 1, (GLfloat*)&xy);
5643}
5644
5645void __stdcall glUniform2fv(GLint location, GLsizei count, const GLfloat* v)
5646{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00005647 EVENT("(GLint location = %d, GLsizei count = %d, const GLfloat* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005648
5649 try
5650 {
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005651 if (count < 0)
5652 {
5653 return error(GL_INVALID_VALUE);
5654 }
daniel@transgaming.com9a95e2b2010-04-13 03:26:03 +00005655
5656 if (location == -1)
5657 {
5658 return;
5659 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005660
daniel@transgaming.com9d788502011-11-09 17:46:55 +00005661 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005662
5663 if (context)
5664 {
5665 gl::Program *program = context->getCurrentProgram();
5666
5667 if (!program)
5668 {
5669 return error(GL_INVALID_OPERATION);
5670 }
5671
5672 if (!program->setUniform2fv(location, count, v))
5673 {
5674 return error(GL_INVALID_OPERATION);
5675 }
5676 }
5677 }
5678 catch(std::bad_alloc&)
5679 {
5680 return error(GL_OUT_OF_MEMORY);
5681 }
5682}
5683
5684void __stdcall glUniform2i(GLint location, GLint x, GLint y)
5685{
5686 GLint xy[4] = {x, y};
5687
5688 glUniform2iv(location, 1, (GLint*)&xy);
5689}
5690
5691void __stdcall glUniform2iv(GLint location, GLsizei count, const GLint* v)
5692{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00005693 EVENT("(GLint location = %d, GLsizei count = %d, const GLint* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005694
5695 try
5696 {
5697 if (count < 0)
5698 {
5699 return error(GL_INVALID_VALUE);
5700 }
5701
daniel@transgaming.com9a95e2b2010-04-13 03:26:03 +00005702 if (location == -1)
5703 {
5704 return;
5705 }
5706
daniel@transgaming.com9d788502011-11-09 17:46:55 +00005707 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com9a95e2b2010-04-13 03:26:03 +00005708
5709 if (context)
5710 {
5711 gl::Program *program = context->getCurrentProgram();
5712
5713 if (!program)
5714 {
5715 return error(GL_INVALID_OPERATION);
5716 }
5717
5718 if (!program->setUniform2iv(location, count, v))
5719 {
5720 return error(GL_INVALID_OPERATION);
5721 }
5722 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005723 }
5724 catch(std::bad_alloc&)
5725 {
5726 return error(GL_OUT_OF_MEMORY);
5727 }
5728}
5729
5730void __stdcall glUniform3f(GLint location, GLfloat x, GLfloat y, GLfloat z)
5731{
5732 GLfloat xyz[3] = {x, y, z};
5733
5734 glUniform3fv(location, 1, (GLfloat*)&xyz);
5735}
5736
5737void __stdcall glUniform3fv(GLint location, GLsizei count, const GLfloat* v)
5738{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00005739 EVENT("(GLint location = %d, GLsizei count = %d, const GLfloat* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005740
5741 try
5742 {
5743 if (count < 0)
5744 {
5745 return error(GL_INVALID_VALUE);
5746 }
5747
5748 if (location == -1)
5749 {
5750 return;
5751 }
5752
daniel@transgaming.com9d788502011-11-09 17:46:55 +00005753 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005754
5755 if (context)
5756 {
5757 gl::Program *program = context->getCurrentProgram();
5758
5759 if (!program)
5760 {
5761 return error(GL_INVALID_OPERATION);
5762 }
5763
5764 if (!program->setUniform3fv(location, count, v))
5765 {
5766 return error(GL_INVALID_OPERATION);
5767 }
5768 }
5769 }
5770 catch(std::bad_alloc&)
5771 {
5772 return error(GL_OUT_OF_MEMORY);
5773 }
5774}
5775
5776void __stdcall glUniform3i(GLint location, GLint x, GLint y, GLint z)
5777{
5778 GLint xyz[3] = {x, y, z};
5779
5780 glUniform3iv(location, 1, (GLint*)&xyz);
5781}
5782
5783void __stdcall glUniform3iv(GLint location, GLsizei count, const GLint* v)
5784{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00005785 EVENT("(GLint location = %d, GLsizei count = %d, const GLint* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005786
5787 try
5788 {
5789 if (count < 0)
5790 {
5791 return error(GL_INVALID_VALUE);
5792 }
5793
daniel@transgaming.com9a95e2b2010-04-13 03:26:03 +00005794 if (location == -1)
5795 {
5796 return;
5797 }
5798
daniel@transgaming.com9d788502011-11-09 17:46:55 +00005799 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com9a95e2b2010-04-13 03:26:03 +00005800
5801 if (context)
5802 {
5803 gl::Program *program = context->getCurrentProgram();
5804
5805 if (!program)
5806 {
5807 return error(GL_INVALID_OPERATION);
5808 }
5809
5810 if (!program->setUniform3iv(location, count, v))
5811 {
5812 return error(GL_INVALID_OPERATION);
5813 }
5814 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005815 }
5816 catch(std::bad_alloc&)
5817 {
5818 return error(GL_OUT_OF_MEMORY);
5819 }
5820}
5821
5822void __stdcall glUniform4f(GLint location, GLfloat x, GLfloat y, GLfloat z, GLfloat w)
5823{
5824 GLfloat xyzw[4] = {x, y, z, w};
5825
5826 glUniform4fv(location, 1, (GLfloat*)&xyzw);
5827}
5828
5829void __stdcall glUniform4fv(GLint location, GLsizei count, const GLfloat* v)
5830{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00005831 EVENT("(GLint location = %d, GLsizei count = %d, const GLfloat* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005832
5833 try
5834 {
5835 if (count < 0)
5836 {
5837 return error(GL_INVALID_VALUE);
5838 }
5839
5840 if (location == -1)
5841 {
5842 return;
5843 }
5844
daniel@transgaming.com9d788502011-11-09 17:46:55 +00005845 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005846
5847 if (context)
5848 {
5849 gl::Program *program = context->getCurrentProgram();
5850
5851 if (!program)
5852 {
5853 return error(GL_INVALID_OPERATION);
5854 }
5855
5856 if (!program->setUniform4fv(location, count, v))
5857 {
5858 return error(GL_INVALID_OPERATION);
5859 }
5860 }
5861 }
5862 catch(std::bad_alloc&)
5863 {
5864 return error(GL_OUT_OF_MEMORY);
5865 }
5866}
5867
5868void __stdcall glUniform4i(GLint location, GLint x, GLint y, GLint z, GLint w)
5869{
5870 GLint xyzw[4] = {x, y, z, w};
5871
5872 glUniform4iv(location, 1, (GLint*)&xyzw);
5873}
5874
5875void __stdcall glUniform4iv(GLint location, GLsizei count, const GLint* v)
5876{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00005877 EVENT("(GLint location = %d, GLsizei count = %d, const GLint* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005878
5879 try
5880 {
5881 if (count < 0)
5882 {
5883 return error(GL_INVALID_VALUE);
5884 }
5885
daniel@transgaming.com9a95e2b2010-04-13 03:26:03 +00005886 if (location == -1)
5887 {
5888 return;
5889 }
5890
daniel@transgaming.com9d788502011-11-09 17:46:55 +00005891 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com9a95e2b2010-04-13 03:26:03 +00005892
5893 if (context)
5894 {
5895 gl::Program *program = context->getCurrentProgram();
5896
5897 if (!program)
5898 {
5899 return error(GL_INVALID_OPERATION);
5900 }
5901
5902 if (!program->setUniform4iv(location, count, v))
5903 {
5904 return error(GL_INVALID_OPERATION);
5905 }
5906 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005907 }
5908 catch(std::bad_alloc&)
5909 {
5910 return error(GL_OUT_OF_MEMORY);
5911 }
5912}
5913
5914void __stdcall glUniformMatrix2fv(GLint location, GLsizei count, GLboolean transpose, const GLfloat* value)
5915{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00005916 EVENT("(GLint location = %d, GLsizei count = %d, GLboolean transpose = %d, const GLfloat* value = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00005917 location, count, transpose, value);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005918
5919 try
5920 {
5921 if (count < 0 || transpose != GL_FALSE)
5922 {
5923 return error(GL_INVALID_VALUE);
5924 }
5925
5926 if (location == -1)
5927 {
5928 return;
5929 }
5930
daniel@transgaming.com9d788502011-11-09 17:46:55 +00005931 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005932
5933 if (context)
5934 {
5935 gl::Program *program = context->getCurrentProgram();
5936
5937 if (!program)
5938 {
5939 return error(GL_INVALID_OPERATION);
5940 }
5941
5942 if (!program->setUniformMatrix2fv(location, count, value))
5943 {
5944 return error(GL_INVALID_OPERATION);
5945 }
5946 }
5947 }
5948 catch(std::bad_alloc&)
5949 {
5950 return error(GL_OUT_OF_MEMORY);
5951 }
5952}
5953
5954void __stdcall glUniformMatrix3fv(GLint location, GLsizei count, GLboolean transpose, const GLfloat* value)
5955{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00005956 EVENT("(GLint location = %d, GLsizei count = %d, GLboolean transpose = %d, const GLfloat* value = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00005957 location, count, transpose, value);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005958
5959 try
5960 {
5961 if (count < 0 || transpose != GL_FALSE)
5962 {
5963 return error(GL_INVALID_VALUE);
5964 }
5965
5966 if (location == -1)
5967 {
5968 return;
5969 }
5970
daniel@transgaming.com9d788502011-11-09 17:46:55 +00005971 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005972
5973 if (context)
5974 {
5975 gl::Program *program = context->getCurrentProgram();
5976
5977 if (!program)
5978 {
5979 return error(GL_INVALID_OPERATION);
5980 }
5981
5982 if (!program->setUniformMatrix3fv(location, count, value))
5983 {
5984 return error(GL_INVALID_OPERATION);
5985 }
5986 }
5987 }
5988 catch(std::bad_alloc&)
5989 {
5990 return error(GL_OUT_OF_MEMORY);
5991 }
5992}
5993
5994void __stdcall glUniformMatrix4fv(GLint location, GLsizei count, GLboolean transpose, const GLfloat* value)
5995{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00005996 EVENT("(GLint location = %d, GLsizei count = %d, GLboolean transpose = %d, const GLfloat* value = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00005997 location, count, transpose, value);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00005998
5999 try
6000 {
6001 if (count < 0 || transpose != GL_FALSE)
6002 {
6003 return error(GL_INVALID_VALUE);
6004 }
6005
6006 if (location == -1)
6007 {
6008 return;
6009 }
6010
daniel@transgaming.com9d788502011-11-09 17:46:55 +00006011 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006012
6013 if (context)
6014 {
6015 gl::Program *program = context->getCurrentProgram();
6016
6017 if (!program)
6018 {
6019 return error(GL_INVALID_OPERATION);
6020 }
6021
6022 if (!program->setUniformMatrix4fv(location, count, value))
6023 {
6024 return error(GL_INVALID_OPERATION);
6025 }
6026 }
6027 }
6028 catch(std::bad_alloc&)
6029 {
6030 return error(GL_OUT_OF_MEMORY);
6031 }
6032}
6033
6034void __stdcall glUseProgram(GLuint program)
6035{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00006036 EVENT("(GLuint program = %d)", program);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006037
6038 try
6039 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00006040 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006041
6042 if (context)
6043 {
6044 gl::Program *programObject = context->getProgram(program);
6045
daniel@transgaming.comc8478202010-04-13 19:53:35 +00006046 if (!programObject && program != 0)
6047 {
6048 if (context->getShader(program))
6049 {
6050 return error(GL_INVALID_OPERATION);
6051 }
6052 else
6053 {
6054 return error(GL_INVALID_VALUE);
6055 }
6056 }
6057
6058 if (program != 0 && !programObject->isLinked())
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006059 {
6060 return error(GL_INVALID_OPERATION);
6061 }
6062
6063 context->useProgram(program);
6064 }
6065 }
6066 catch(std::bad_alloc&)
6067 {
6068 return error(GL_OUT_OF_MEMORY);
6069 }
6070}
6071
6072void __stdcall glValidateProgram(GLuint program)
6073{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00006074 EVENT("(GLuint program = %d)", program);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006075
6076 try
6077 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00006078 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com86a7a132010-04-29 03:32:32 +00006079
6080 if (context)
6081 {
6082 gl::Program *programObject = context->getProgram(program);
6083
6084 if (!programObject)
6085 {
6086 if (context->getShader(program))
6087 {
6088 return error(GL_INVALID_OPERATION);
6089 }
6090 else
6091 {
6092 return error(GL_INVALID_VALUE);
6093 }
6094 }
6095
6096 programObject->validate();
6097 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006098 }
6099 catch(std::bad_alloc&)
6100 {
6101 return error(GL_OUT_OF_MEMORY);
6102 }
6103}
6104
6105void __stdcall glVertexAttrib1f(GLuint index, GLfloat x)
6106{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00006107 EVENT("(GLuint index = %d, GLfloat x = %f)", index, x);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006108
6109 try
6110 {
6111 if (index >= gl::MAX_VERTEX_ATTRIBS)
6112 {
6113 return error(GL_INVALID_VALUE);
6114 }
6115
daniel@transgaming.com9d788502011-11-09 17:46:55 +00006116 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.come4b08c82010-04-20 18:53:06 +00006117
6118 if (context)
6119 {
6120 GLfloat vals[4] = { x, 0, 0, 1 };
6121 context->setVertexAttrib(index, vals);
6122 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006123 }
6124 catch(std::bad_alloc&)
6125 {
6126 return error(GL_OUT_OF_MEMORY);
6127 }
6128}
6129
6130void __stdcall glVertexAttrib1fv(GLuint index, const GLfloat* values)
6131{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00006132 EVENT("(GLuint index = %d, const GLfloat* values = 0x%0.8p)", index, values);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006133
6134 try
6135 {
6136 if (index >= gl::MAX_VERTEX_ATTRIBS)
6137 {
6138 return error(GL_INVALID_VALUE);
6139 }
6140
daniel@transgaming.com9d788502011-11-09 17:46:55 +00006141 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.come4b08c82010-04-20 18:53:06 +00006142
6143 if (context)
6144 {
6145 GLfloat vals[4] = { values[0], 0, 0, 1 };
6146 context->setVertexAttrib(index, vals);
6147 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006148 }
6149 catch(std::bad_alloc&)
6150 {
6151 return error(GL_OUT_OF_MEMORY);
6152 }
6153}
6154
6155void __stdcall glVertexAttrib2f(GLuint index, GLfloat x, GLfloat y)
6156{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00006157 EVENT("(GLuint index = %d, GLfloat x = %f, GLfloat y = %f)", index, x, y);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006158
6159 try
6160 {
6161 if (index >= gl::MAX_VERTEX_ATTRIBS)
6162 {
6163 return error(GL_INVALID_VALUE);
6164 }
6165
daniel@transgaming.com9d788502011-11-09 17:46:55 +00006166 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.come4b08c82010-04-20 18:53:06 +00006167
6168 if (context)
6169 {
6170 GLfloat vals[4] = { x, y, 0, 1 };
6171 context->setVertexAttrib(index, vals);
6172 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006173 }
6174 catch(std::bad_alloc&)
6175 {
6176 return error(GL_OUT_OF_MEMORY);
6177 }
6178}
6179
6180void __stdcall glVertexAttrib2fv(GLuint index, const GLfloat* values)
6181{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00006182 EVENT("(GLuint index = %d, const GLfloat* values = 0x%0.8p)", index, values);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006183
6184 try
6185 {
6186 if (index >= gl::MAX_VERTEX_ATTRIBS)
6187 {
6188 return error(GL_INVALID_VALUE);
6189 }
6190
daniel@transgaming.com9d788502011-11-09 17:46:55 +00006191 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.come4b08c82010-04-20 18:53:06 +00006192
6193 if (context)
6194 {
6195 GLfloat vals[4] = { values[0], values[1], 0, 1 };
6196 context->setVertexAttrib(index, vals);
6197 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006198 }
6199 catch(std::bad_alloc&)
6200 {
6201 return error(GL_OUT_OF_MEMORY);
6202 }
6203}
6204
6205void __stdcall glVertexAttrib3f(GLuint index, GLfloat x, GLfloat y, GLfloat z)
6206{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00006207 EVENT("(GLuint index = %d, GLfloat x = %f, GLfloat y = %f, GLfloat z = %f)", index, x, y, z);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006208
6209 try
6210 {
6211 if (index >= gl::MAX_VERTEX_ATTRIBS)
6212 {
6213 return error(GL_INVALID_VALUE);
6214 }
6215
daniel@transgaming.com9d788502011-11-09 17:46:55 +00006216 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.come4b08c82010-04-20 18:53:06 +00006217
6218 if (context)
6219 {
6220 GLfloat vals[4] = { x, y, z, 1 };
6221 context->setVertexAttrib(index, vals);
6222 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006223 }
6224 catch(std::bad_alloc&)
6225 {
6226 return error(GL_OUT_OF_MEMORY);
6227 }
6228}
6229
6230void __stdcall glVertexAttrib3fv(GLuint index, const GLfloat* values)
6231{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00006232 EVENT("(GLuint index = %d, const GLfloat* values = 0x%0.8p)", index, values);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006233
6234 try
6235 {
6236 if (index >= gl::MAX_VERTEX_ATTRIBS)
6237 {
6238 return error(GL_INVALID_VALUE);
6239 }
6240
daniel@transgaming.com9d788502011-11-09 17:46:55 +00006241 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.come4b08c82010-04-20 18:53:06 +00006242
6243 if (context)
6244 {
6245 GLfloat vals[4] = { values[0], values[1], values[2], 1 };
6246 context->setVertexAttrib(index, vals);
6247 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006248 }
6249 catch(std::bad_alloc&)
6250 {
6251 return error(GL_OUT_OF_MEMORY);
6252 }
6253}
6254
6255void __stdcall glVertexAttrib4f(GLuint index, GLfloat x, GLfloat y, GLfloat z, GLfloat w)
6256{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00006257 EVENT("(GLuint index = %d, GLfloat x = %f, GLfloat y = %f, GLfloat z = %f, GLfloat w = %f)", index, x, y, z, w);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006258
6259 try
6260 {
6261 if (index >= gl::MAX_VERTEX_ATTRIBS)
6262 {
6263 return error(GL_INVALID_VALUE);
6264 }
6265
daniel@transgaming.com9d788502011-11-09 17:46:55 +00006266 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.come4b08c82010-04-20 18:53:06 +00006267
6268 if (context)
6269 {
6270 GLfloat vals[4] = { x, y, z, w };
6271 context->setVertexAttrib(index, vals);
6272 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006273 }
6274 catch(std::bad_alloc&)
6275 {
6276 return error(GL_OUT_OF_MEMORY);
6277 }
6278}
6279
6280void __stdcall glVertexAttrib4fv(GLuint index, const GLfloat* values)
6281{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00006282 EVENT("(GLuint index = %d, const GLfloat* values = 0x%0.8p)", index, values);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006283
6284 try
6285 {
6286 if (index >= gl::MAX_VERTEX_ATTRIBS)
6287 {
6288 return error(GL_INVALID_VALUE);
6289 }
6290
daniel@transgaming.com9d788502011-11-09 17:46:55 +00006291 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.come4b08c82010-04-20 18:53:06 +00006292
6293 if (context)
6294 {
6295 context->setVertexAttrib(index, values);
6296 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006297 }
6298 catch(std::bad_alloc&)
6299 {
6300 return error(GL_OUT_OF_MEMORY);
6301 }
6302}
6303
daniel@transgaming.comd2820bf2012-01-27 15:38:48 +00006304void __stdcall glVertexAttribDivisorANGLE(GLuint index, GLuint divisor)
6305{
6306 EVENT("(GLuint index = %d, GLuint divisor = %d)", index, divisor);
6307
6308 try
6309 {
6310 if (index >= gl::MAX_VERTEX_ATTRIBS)
6311 {
6312 return error(GL_INVALID_VALUE);
6313 }
6314
6315 gl::Context *context = gl::getNonLostContext();
6316
6317 if (context)
6318 {
6319 context->setVertexAttribDivisor(index, divisor);
6320 }
6321 }
6322 catch(std::bad_alloc&)
6323 {
6324 return error(GL_OUT_OF_MEMORY);
6325 }
6326}
6327
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00006328void __stdcall glVertexAttribPointer(GLuint index, GLint size, GLenum type, GLboolean normalized, GLsizei stride, const GLvoid* ptr)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006329{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00006330 EVENT("(GLuint index = %d, GLint size = %d, GLenum type = 0x%X, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00006331 "GLboolean normalized = %d, GLsizei stride = %d, const GLvoid* ptr = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00006332 index, size, type, normalized, stride, ptr);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006333
6334 try
6335 {
6336 if (index >= gl::MAX_VERTEX_ATTRIBS)
6337 {
6338 return error(GL_INVALID_VALUE);
6339 }
6340
6341 if (size < 1 || size > 4)
6342 {
6343 return error(GL_INVALID_VALUE);
6344 }
6345
6346 switch (type)
6347 {
6348 case GL_BYTE:
6349 case GL_UNSIGNED_BYTE:
6350 case GL_SHORT:
6351 case GL_UNSIGNED_SHORT:
6352 case GL_FIXED:
6353 case GL_FLOAT:
6354 break;
6355 default:
6356 return error(GL_INVALID_ENUM);
6357 }
6358
6359 if (stride < 0)
6360 {
6361 return error(GL_INVALID_VALUE);
6362 }
6363
daniel@transgaming.com9d788502011-11-09 17:46:55 +00006364 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006365
6366 if (context)
6367 {
daniel@transgaming.com9ecb9f92010-07-28 19:21:12 +00006368 context->setVertexAttribState(index, context->getArrayBuffer(), size, type, (normalized == GL_TRUE), stride, ptr);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006369 }
6370 }
6371 catch(std::bad_alloc&)
6372 {
6373 return error(GL_OUT_OF_MEMORY);
6374 }
6375}
6376
6377void __stdcall glViewport(GLint x, GLint y, GLsizei width, GLsizei height)
6378{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00006379 EVENT("(GLint x = %d, GLint y = %d, GLsizei width = %d, GLsizei height = %d)", x, y, width, height);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006380
6381 try
6382 {
6383 if (width < 0 || height < 0)
6384 {
6385 return error(GL_INVALID_VALUE);
6386 }
6387
daniel@transgaming.com9d788502011-11-09 17:46:55 +00006388 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006389
6390 if (context)
6391 {
daniel@transgaming.com428d1582010-05-04 03:35:25 +00006392 context->setViewportParams(x, y, width, height);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006393 }
6394 }
6395 catch(std::bad_alloc&)
6396 {
6397 return error(GL_OUT_OF_MEMORY);
6398 }
6399}
6400
daniel@transgaming.com4cbc5902010-08-24 19:20:26 +00006401void __stdcall glBlitFramebufferANGLE(GLint srcX0, GLint srcY0, GLint srcX1, GLint srcY1, GLint dstX0, GLint dstY0, GLint dstX1, GLint dstY1,
6402 GLbitfield mask, GLenum filter)
6403{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00006404 EVENT("(GLint srcX0 = %d, GLint srcY0 = %d, GLint srcX1 = %d, GLint srcY1 = %d, "
daniel@transgaming.com4cbc5902010-08-24 19:20:26 +00006405 "GLint dstX0 = %d, GLint dstY0 = %d, GLint dstX1 = %d, GLint dstY1 = %d, "
6406 "GLbitfield mask = 0x%X, GLenum filter = 0x%X)",
6407 srcX0, srcY0, srcX1, srcX1, dstX0, dstY0, dstX1, dstY1, mask, filter);
6408
6409 try
6410 {
6411 switch (filter)
6412 {
6413 case GL_NEAREST:
6414 break;
6415 default:
6416 return error(GL_INVALID_ENUM);
6417 }
6418
6419 if ((mask & ~(GL_COLOR_BUFFER_BIT | GL_STENCIL_BUFFER_BIT | GL_DEPTH_BUFFER_BIT)) != 0)
6420 {
6421 return error(GL_INVALID_VALUE);
6422 }
6423
6424 if (srcX1 - srcX0 != dstX1 - dstX0 || srcY1 - srcY0 != dstY1 - dstY0)
6425 {
6426 ERR("Scaling and flipping in BlitFramebufferANGLE not supported by this implementation");
6427 return error(GL_INVALID_OPERATION);
6428 }
6429
daniel@transgaming.com9d788502011-11-09 17:46:55 +00006430 gl::Context *context = gl::getNonLostContext();
daniel@transgaming.com4cbc5902010-08-24 19:20:26 +00006431
6432 if (context)
6433 {
6434 if (context->getReadFramebufferHandle() == context->getDrawFramebufferHandle())
6435 {
6436 ERR("Blits with the same source and destination framebuffer are not supported by this implementation.");
6437 return error(GL_INVALID_OPERATION);
6438 }
6439
6440 context->blitFramebuffer(srcX0, srcY0, srcX1, srcY1, dstX0, dstY0, dstX1, dstY1, mask);
6441 }
6442 }
6443 catch(std::bad_alloc&)
6444 {
6445 return error(GL_OUT_OF_MEMORY);
6446 }
6447}
6448
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00006449void __stdcall glTexImage3DOES(GLenum target, GLint level, GLenum internalformat, GLsizei width, GLsizei height, GLsizei depth,
6450 GLint border, GLenum format, GLenum type, const GLvoid* pixels)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006451{
apatrick@chromium.org0f4cefe2011-01-26 19:30:57 +00006452 EVENT("(GLenum target = 0x%X, GLint level = %d, GLenum internalformat = 0x%X, "
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00006453 "GLsizei width = %d, GLsizei height = %d, GLsizei depth = %d, GLint border = %d, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00006454 "GLenum format = 0x%X, GLenum type = 0x%x, const GLvoid* pixels = 0x%0.8p)",
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006455 target, level, internalformat, width, height, depth, border, format, type, pixels);
6456
6457 try
6458 {
6459 UNIMPLEMENTED(); // FIXME
6460 }
6461 catch(std::bad_alloc&)
6462 {
6463 return error(GL_OUT_OF_MEMORY);
6464 }
6465}
daniel@transgaming.comce3d0f22010-05-04 03:35:14 +00006466
6467__eglMustCastToProperFunctionPointerType __stdcall glGetProcAddress(const char *procname)
6468{
6469 struct Extension
6470 {
6471 const char *name;
6472 __eglMustCastToProperFunctionPointerType address;
6473 };
6474
6475 static const Extension glExtensions[] =
6476 {
6477 {"glTexImage3DOES", (__eglMustCastToProperFunctionPointerType)glTexImage3DOES},
daniel@transgaming.com01868132010-08-24 19:21:17 +00006478 {"glBlitFramebufferANGLE", (__eglMustCastToProperFunctionPointerType)glBlitFramebufferANGLE},
daniel@transgaming.com1fe96c92011-01-14 15:08:44 +00006479 {"glRenderbufferStorageMultisampleANGLE", (__eglMustCastToProperFunctionPointerType)glRenderbufferStorageMultisampleANGLE},
apatrick@chromium.orgd3bd0ad2010-08-30 18:55:36 +00006480 {"glDeleteFencesNV", (__eglMustCastToProperFunctionPointerType)glDeleteFencesNV},
6481 {"glGenFencesNV", (__eglMustCastToProperFunctionPointerType)glGenFencesNV},
6482 {"glIsFenceNV", (__eglMustCastToProperFunctionPointerType)glIsFenceNV},
6483 {"glTestFenceNV", (__eglMustCastToProperFunctionPointerType)glTestFenceNV},
6484 {"glGetFenceivNV", (__eglMustCastToProperFunctionPointerType)glGetFenceivNV},
6485 {"glFinishFenceNV", (__eglMustCastToProperFunctionPointerType)glFinishFenceNV},
6486 {"glSetFenceNV", (__eglMustCastToProperFunctionPointerType)glSetFenceNV},
zmo@google.coma574f782011-10-03 21:45:23 +00006487 {"glGetTranslatedShaderSourceANGLE", (__eglMustCastToProperFunctionPointerType)glGetTranslatedShaderSourceANGLE},
daniel@transgaming.com0bd1f2f2011-11-11 04:19:03 +00006488 {"glTexStorage2DEXT", (__eglMustCastToProperFunctionPointerType)glTexStorage2DEXT},
daniel@transgaming.com709ed112011-11-12 03:18:10 +00006489 {"glGetGraphicsResetStatusEXT", (__eglMustCastToProperFunctionPointerType)glGetGraphicsResetStatusEXT},
6490 {"glReadnPixelsEXT", (__eglMustCastToProperFunctionPointerType)glReadnPixelsEXT},
6491 {"glGetnUniformfvEXT", (__eglMustCastToProperFunctionPointerType)glGetnUniformfvEXT},
6492 {"glGetnUniformivEXT", (__eglMustCastToProperFunctionPointerType)glGetnUniformivEXT},
daniel@transgaming.com86bdb822012-01-20 18:24:39 +00006493 {"glGenQueriesEXT", (__eglMustCastToProperFunctionPointerType)glGenQueriesEXT},
6494 {"glDeleteQueriesEXT", (__eglMustCastToProperFunctionPointerType)glDeleteQueriesEXT},
6495 {"glIsQueryEXT", (__eglMustCastToProperFunctionPointerType)glIsQueryEXT},
6496 {"glBeginQueryEXT", (__eglMustCastToProperFunctionPointerType)glBeginQueryEXT},
6497 {"glEndQueryEXT", (__eglMustCastToProperFunctionPointerType)glEndQueryEXT},
6498 {"glGetQueryivEXT", (__eglMustCastToProperFunctionPointerType)glGetQueryivEXT},
6499 {"glGetQueryObjectuivEXT", (__eglMustCastToProperFunctionPointerType)glGetQueryObjectuivEXT},
daniel@transgaming.comce3d0f22010-05-04 03:35:14 +00006500 };
6501
6502 for (int ext = 0; ext < sizeof(glExtensions) / sizeof(Extension); ext++)
6503 {
6504 if (strcmp(procname, glExtensions[ext].name) == 0)
6505 {
6506 return (__eglMustCastToProperFunctionPointerType)glExtensions[ext].address;
6507 }
6508 }
6509
6510 return NULL;
6511}
6512
daniel@transgaming.com17f548c2011-11-09 17:47:02 +00006513// Non-public functions used by EGL
6514
daniel@transgaming.com64a0fb22011-11-11 04:10:40 +00006515bool __stdcall glBindTexImage(egl::Surface *surface)
jbauman@chromium.orgae345802011-03-30 22:04:25 +00006516{
6517 EVENT("(egl::Surface* surface = 0x%0.8p)",
6518 surface);
6519
6520 try
6521 {
daniel@transgaming.com9d788502011-11-09 17:46:55 +00006522 gl::Context *context = gl::getNonLostContext();
jbauman@chromium.orgae345802011-03-30 22:04:25 +00006523
6524 if (context)
6525 {
6526 gl::Texture2D *textureObject = context->getTexture2D();
6527
daniel@transgaming.com64a0fb22011-11-11 04:10:40 +00006528 if (textureObject->isImmutable())
6529 {
6530 return false;
6531 }
6532
jbauman@chromium.orgae345802011-03-30 22:04:25 +00006533 if (textureObject)
6534 {
6535 textureObject->bindTexImage(surface);
6536 }
6537 }
6538 }
6539 catch(std::bad_alloc&)
6540 {
daniel@transgaming.com64a0fb22011-11-11 04:10:40 +00006541 return error(GL_OUT_OF_MEMORY, false);
jbauman@chromium.orgae345802011-03-30 22:04:25 +00006542 }
daniel@transgaming.com64a0fb22011-11-11 04:10:40 +00006543
6544 return true;
jbauman@chromium.orgae345802011-03-30 22:04:25 +00006545}
6546
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00006547}