blob: 13f6e217dbea984829c4b7f863339330ac89672b [file] [log] [blame]
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001//
2// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
3// 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
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000016#include "Context.h"
17#include "main.h"
18#include "Program.h"
19#include "Shader.h"
20#include "Buffer.h"
21#include "Texture.h"
22#include "Renderbuffer.h"
23#include "Framebuffer.h"
24#include "mathutil.h"
alokp@chromium.orgea0e1af2010-03-22 19:33:14 +000025#include "common/debug.h"
daniel@transgaming.com00c75962010-03-11 20:36:15 +000026#include "utilities.h"
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000027
28extern "C"
29{
30
31void __stdcall glActiveTexture(GLenum texture)
32{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +000033 TRACE("(GLenum texture = 0x%X)", texture);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000034
35 try
36 {
37 if (texture < GL_TEXTURE0 || texture > GL_TEXTURE0 + gl::MAX_TEXTURE_IMAGE_UNITS - 1)
38 {
39 return error(GL_INVALID_ENUM);
40 }
41
42 gl::Context *context = gl::getContext();
43
44 if (context)
45 {
46 context->activeSampler = texture - GL_TEXTURE0;
47 }
48 }
49 catch(std::bad_alloc&)
50 {
51 return error(GL_OUT_OF_MEMORY);
52 }
53}
54
55void __stdcall glAttachShader(GLuint program, GLuint shader)
56{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +000057 TRACE("(GLuint program = %d, GLuint shader = %d)", program, shader);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000058
59 try
60 {
61 gl::Context *context = gl::getContext();
62
63 if (context)
64 {
65 gl::Program *programObject = context->getProgram(program);
66 gl::Shader *shaderObject = context->getShader(shader);
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +000067
daniel@transgaming.come2b22122010-03-11 19:22:14 +000068 if (!programObject || !shaderObject)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000069 {
70 return error(GL_INVALID_VALUE);
71 }
72
73 if (!programObject->attachShader(shaderObject))
74 {
75 return error(GL_INVALID_OPERATION);
76 }
77 }
78 }
79 catch(std::bad_alloc&)
80 {
81 return error(GL_OUT_OF_MEMORY);
82 }
83}
84
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +000085void __stdcall glBindAttribLocation(GLuint program, GLuint index, const GLchar* name)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000086{
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +000087 TRACE("(GLuint program = %d, GLuint index = %d, const GLchar* name = 0x%0.8p)", program, index, name);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000088
89 try
90 {
91 if (index >= gl::MAX_VERTEX_ATTRIBS)
92 {
93 return error(GL_INVALID_VALUE);
94 }
95
96 gl::Context *context = gl::getContext();
97
98 if (context)
99 {
100 gl::Program *programObject = context->getProgram(program);
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +0000101
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000102 if (!programObject)
103 {
104 return error(GL_INVALID_VALUE);
105 }
106
107 programObject->bindAttributeLocation(index, name);
108 }
109 }
110 catch(std::bad_alloc&)
111 {
112 return error(GL_OUT_OF_MEMORY);
113 }
114}
115
116void __stdcall glBindBuffer(GLenum target, GLuint buffer)
117{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000118 TRACE("(GLenum target = 0x%X, GLuint buffer = %d)", target, buffer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000119
120 try
121 {
122 gl::Context *context = gl::getContext();
123
124 if (context)
125 {
126 switch (target)
127 {
128 case GL_ARRAY_BUFFER:
129 context->bindArrayBuffer(buffer);
130 return;
131 case GL_ELEMENT_ARRAY_BUFFER:
132 context->bindElementArrayBuffer(buffer);
133 return;
134 default:
135 return error(GL_INVALID_ENUM);
136 }
137 }
138 }
139 catch(std::bad_alloc&)
140 {
141 return error(GL_OUT_OF_MEMORY);
142 }
143}
144
145void __stdcall glBindFramebuffer(GLenum target, GLuint framebuffer)
146{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000147 TRACE("(GLenum target = 0x%X, GLuint framebuffer = %d)", target, framebuffer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000148
149 try
150 {
151 if (target != GL_FRAMEBUFFER)
152 {
153 return error(GL_INVALID_ENUM);
154 }
155
156 gl::Context *context = gl::getContext();
157
158 if (context)
159 {
160 context->bindFramebuffer(framebuffer);
161 }
162 }
163 catch(std::bad_alloc&)
164 {
165 return error(GL_OUT_OF_MEMORY);
166 }
167}
168
169void __stdcall glBindRenderbuffer(GLenum target, GLuint renderbuffer)
170{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000171 TRACE("(GLenum target = 0x%X, GLuint renderbuffer = %d)", target, renderbuffer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000172
173 try
174 {
175 if (target != GL_RENDERBUFFER)
176 {
177 return error(GL_INVALID_ENUM);
178 }
179
180 gl::Context *context = gl::getContext();
181
182 if (context)
183 {
184 context->bindRenderbuffer(renderbuffer);
185 }
186 }
187 catch(std::bad_alloc&)
188 {
189 return error(GL_OUT_OF_MEMORY);
190 }
191}
192
193void __stdcall glBindTexture(GLenum target, GLuint texture)
194{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000195 TRACE("(GLenum target = 0x%X, GLuint texture = %d)", target, texture);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000196
197 try
198 {
199 gl::Context *context = gl::getContext();
200
201 if (context)
202 {
203 gl::Texture *textureObject = context->getTexture(texture);
204
205 if (textureObject && textureObject->getTarget() != target && texture != 0)
206 {
207 return error(GL_INVALID_OPERATION);
208 }
209
210 switch (target)
211 {
212 case GL_TEXTURE_2D:
213 context->bindTexture2D(texture);
214 return;
215 case GL_TEXTURE_CUBE_MAP:
216 context->bindTextureCubeMap(texture);
217 return;
218 default:
219 return error(GL_INVALID_ENUM);
220 }
221 }
222 }
223 catch(std::bad_alloc&)
224 {
225 return error(GL_OUT_OF_MEMORY);
226 }
227}
228
229void __stdcall glBlendColor(GLclampf red, GLclampf green, GLclampf blue, GLclampf alpha)
230{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000231 TRACE("(GLclampf red = %f, GLclampf green = %f, GLclampf blue = %f, GLclampf alpha = %f)",
232 red, green, blue, alpha);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000233
234 try
235 {
236 gl::Context* context = gl::getContext();
237
238 if (context)
239 {
240 context->blendColor.red = gl::clamp01(red);
241 context->blendColor.blue = gl::clamp01(blue);
242 context->blendColor.green = gl::clamp01(green);
243 context->blendColor.alpha = gl::clamp01(alpha);
244 }
245 }
246 catch(std::bad_alloc&)
247 {
248 return error(GL_OUT_OF_MEMORY);
249 }
250}
251
252void __stdcall glBlendEquation(GLenum mode)
253{
254 glBlendEquationSeparate(mode, mode);
255}
256
257void __stdcall glBlendEquationSeparate(GLenum modeRGB, GLenum modeAlpha)
258{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000259 TRACE("(GLenum modeRGB = 0x%X, GLenum modeAlpha = 0x%X)", modeRGB, modeAlpha);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000260
261 try
262 {
263 switch (modeRGB)
264 {
265 case GL_FUNC_ADD:
266 case GL_FUNC_SUBTRACT:
267 case GL_FUNC_REVERSE_SUBTRACT:
268 break;
269 default:
270 return error(GL_INVALID_ENUM);
271 }
272
273 switch (modeAlpha)
274 {
275 case GL_FUNC_ADD:
276 case GL_FUNC_SUBTRACT:
277 case GL_FUNC_REVERSE_SUBTRACT:
278 break;
279 default:
280 return error(GL_INVALID_ENUM);
281 }
282
283 gl::Context *context = gl::getContext();
284
285 if (context)
286 {
287 context->blendEquationRGB = modeRGB;
288 context->blendEquationAlpha = modeAlpha;
289 }
290 }
291 catch(std::bad_alloc&)
292 {
293 return error(GL_OUT_OF_MEMORY);
294 }
295}
296
297void __stdcall glBlendFunc(GLenum sfactor, GLenum dfactor)
298{
299 glBlendFuncSeparate(sfactor, dfactor, sfactor, dfactor);
300}
301
302void __stdcall glBlendFuncSeparate(GLenum srcRGB, GLenum dstRGB, GLenum srcAlpha, GLenum dstAlpha)
303{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000304 TRACE("(GLenum srcRGB = 0x%X, GLenum dstRGB = 0x%X, GLenum srcAlpha = 0x%X, GLenum dstAlpha = 0x%X)",
305 srcRGB, dstRGB, srcAlpha, dstAlpha);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000306
307 try
308 {
309 switch (srcRGB)
310 {
311 case GL_ZERO:
312 case GL_ONE:
313 case GL_SRC_COLOR:
314 case GL_ONE_MINUS_SRC_COLOR:
315 case GL_DST_COLOR:
316 case GL_ONE_MINUS_DST_COLOR:
317 case GL_SRC_ALPHA:
318 case GL_ONE_MINUS_SRC_ALPHA:
319 case GL_DST_ALPHA:
320 case GL_ONE_MINUS_DST_ALPHA:
321 case GL_CONSTANT_COLOR:
322 case GL_ONE_MINUS_CONSTANT_COLOR:
323 case GL_CONSTANT_ALPHA:
324 case GL_ONE_MINUS_CONSTANT_ALPHA:
325 case GL_SRC_ALPHA_SATURATE:
326 break;
327 default:
328 return error(GL_INVALID_ENUM);
329 }
330
331 switch (dstRGB)
332 {
333 case GL_ZERO:
334 case GL_ONE:
335 case GL_SRC_COLOR:
336 case GL_ONE_MINUS_SRC_COLOR:
337 case GL_DST_COLOR:
338 case GL_ONE_MINUS_DST_COLOR:
339 case GL_SRC_ALPHA:
340 case GL_ONE_MINUS_SRC_ALPHA:
341 case GL_DST_ALPHA:
342 case GL_ONE_MINUS_DST_ALPHA:
343 case GL_CONSTANT_COLOR:
344 case GL_ONE_MINUS_CONSTANT_COLOR:
345 case GL_CONSTANT_ALPHA:
346 case GL_ONE_MINUS_CONSTANT_ALPHA:
347 break;
348 default:
349 return error(GL_INVALID_ENUM);
350 }
351
352 switch (srcAlpha)
353 {
354 case GL_ZERO:
355 case GL_ONE:
356 case GL_SRC_COLOR:
357 case GL_ONE_MINUS_SRC_COLOR:
358 case GL_DST_COLOR:
359 case GL_ONE_MINUS_DST_COLOR:
360 case GL_SRC_ALPHA:
361 case GL_ONE_MINUS_SRC_ALPHA:
362 case GL_DST_ALPHA:
363 case GL_ONE_MINUS_DST_ALPHA:
364 case GL_CONSTANT_COLOR:
365 case GL_ONE_MINUS_CONSTANT_COLOR:
366 case GL_CONSTANT_ALPHA:
367 case GL_ONE_MINUS_CONSTANT_ALPHA:
368 case GL_SRC_ALPHA_SATURATE:
369 break;
370 default:
371 return error(GL_INVALID_ENUM);
372 }
373
374 switch (dstAlpha)
375 {
376 case GL_ZERO:
377 case GL_ONE:
378 case GL_SRC_COLOR:
379 case GL_ONE_MINUS_SRC_COLOR:
380 case GL_DST_COLOR:
381 case GL_ONE_MINUS_DST_COLOR:
382 case GL_SRC_ALPHA:
383 case GL_ONE_MINUS_SRC_ALPHA:
384 case GL_DST_ALPHA:
385 case GL_ONE_MINUS_DST_ALPHA:
386 case GL_CONSTANT_COLOR:
387 case GL_ONE_MINUS_CONSTANT_COLOR:
388 case GL_CONSTANT_ALPHA:
389 case GL_ONE_MINUS_CONSTANT_ALPHA:
390 break;
391 default:
392 return error(GL_INVALID_ENUM);
393 }
394
daniel@transgaming.comfe453652010-03-16 06:23:28 +0000395 bool constantColorUsed = (srcRGB == GL_CONSTANT_COLOR || srcRGB == GL_ONE_MINUS_CONSTANT_COLOR ||
396 dstRGB == GL_CONSTANT_COLOR || dstRGB == GL_ONE_MINUS_CONSTANT_COLOR);
397
398 bool constantAlphaUsed = (srcRGB == GL_CONSTANT_ALPHA || srcRGB == GL_ONE_MINUS_CONSTANT_ALPHA ||
399 dstRGB == GL_CONSTANT_ALPHA || dstRGB == GL_ONE_MINUS_CONSTANT_ALPHA);
400
401 if (constantColorUsed && constantAlphaUsed)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000402 {
daniel@transgaming.comfe453652010-03-16 06:23:28 +0000403 ERR("Simultaneous use of GL_CONSTANT_ALPHA/GL_ONE_MINUS_CONSTANT_ALPHA and GL_CONSTANT_COLOR/GL_ONE_MINUS_CONSTANT_COLOR invalid under WebGL");
404 return error(GL_INVALID_OPERATION);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000405 }
406
407 gl::Context *context = gl::getContext();
408
409 if (context)
410 {
411 context->sourceBlendRGB = srcRGB;
412 context->sourceBlendAlpha = srcAlpha;
413 context->destBlendRGB = dstRGB;
414 context->destBlendAlpha = dstAlpha;
415 }
416 }
417 catch(std::bad_alloc&)
418 {
419 return error(GL_OUT_OF_MEMORY);
420 }
421}
422
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +0000423void __stdcall glBufferData(GLenum target, GLsizeiptr size, const GLvoid* data, GLenum usage)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000424{
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +0000425 TRACE("(GLenum target = 0x%X, GLsizeiptr size = %d, const GLvoid* data = 0x%0.8p, GLenum usage = %d)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000426 target, size, data, usage);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000427
428 try
429 {
430 if (size < 0)
431 {
432 return error(GL_INVALID_VALUE);
433 }
434
435 switch (usage)
436 {
437 case GL_STREAM_DRAW:
438 case GL_STATIC_DRAW:
439 case GL_DYNAMIC_DRAW:
440 break;
441 default:
442 return error(GL_INVALID_ENUM);
443 }
444
445 gl::Context *context = gl::getContext();
446
447 if (context)
448 {
449 gl::Buffer *buffer;
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +0000450
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000451 switch (target)
452 {
453 case GL_ARRAY_BUFFER:
454 buffer = context->getArrayBuffer();
455 break;
456 case GL_ELEMENT_ARRAY_BUFFER:
457 buffer = context->getElementArrayBuffer();
458 break;
459 default:
460 return error(GL_INVALID_ENUM);
461 }
462
463 if (!buffer)
464 {
465 return error(GL_INVALID_OPERATION);
466 }
467
daniel@transgaming.com0f7aaf52010-03-11 19:41:38 +0000468 buffer->bufferData(data, size, usage);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000469 }
470 }
471 catch(std::bad_alloc&)
472 {
473 return error(GL_OUT_OF_MEMORY);
474 }
475}
476
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +0000477void __stdcall glBufferSubData(GLenum target, GLintptr offset, GLsizeiptr size, const GLvoid* data)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000478{
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +0000479 TRACE("(GLenum target = 0x%X, GLintptr offset = %d, GLsizeiptr size = %d, const GLvoid* data = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000480 target, offset, size, data);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000481
482 try
483 {
484 if (size < 0)
485 {
486 return error(GL_INVALID_VALUE);
487 }
488
daniel@transgaming.comd4620a32010-03-21 04:31:28 +0000489 if (data == NULL)
490 {
491 return;
492 }
493
daniel@transgaming.com0f7aaf52010-03-11 19:41:38 +0000494 gl::Context *context = gl::getContext();
495
496 if (context)
497 {
498 gl::Buffer *buffer;
499
500 switch (target)
501 {
502 case GL_ARRAY_BUFFER:
503 buffer = context->getArrayBuffer();
504 break;
505 case GL_ELEMENT_ARRAY_BUFFER:
506 buffer = context->getElementArrayBuffer();
507 break;
508 default:
509 return error(GL_INVALID_ENUM);
510 }
511
512 if (!buffer)
513 {
514 return error(GL_INVALID_OPERATION);
515 }
516
517 GLenum err = buffer->bufferSubData(data, size, offset);
518
519 if (err != GL_NO_ERROR)
520 {
521 return error(err);
522 }
523 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000524 }
525 catch(std::bad_alloc&)
526 {
527 return error(GL_OUT_OF_MEMORY);
528 }
529}
530
531GLenum __stdcall glCheckFramebufferStatus(GLenum target)
532{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000533 TRACE("(GLenum target = 0x%X)", target);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000534
535 try
536 {
537 if (target != GL_FRAMEBUFFER)
538 {
539 return error(GL_INVALID_ENUM, 0);
540 }
541
542 gl::Context *context = gl::getContext();
543
544 if (context)
545 {
546 gl::Framebuffer *framebuffer = context->getFramebuffer();
547
548 return framebuffer->completeness();
549 }
550 }
551 catch(std::bad_alloc&)
552 {
553 return error(GL_OUT_OF_MEMORY, 0);
554 }
555
556 return 0;
557}
558
559void __stdcall glClear(GLbitfield mask)
560{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000561 TRACE("(GLbitfield mask = %X)", mask);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000562
563 try
564 {
565 gl::Context *context = gl::getContext();
566
567 if (context)
568 {
569 context->clear(mask);
570 }
571 }
572 catch(std::bad_alloc&)
573 {
574 return error(GL_OUT_OF_MEMORY);
575 }
576}
577
578void __stdcall glClearColor(GLclampf red, GLclampf green, GLclampf blue, GLclampf alpha)
579{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000580 TRACE("(GLclampf red = %f, GLclampf green = %f, GLclampf blue = %f, GLclampf alpha = %f)",
581 red, green, blue, alpha);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000582
583 try
584 {
585 gl::Context *context = gl::getContext();
586
587 if (context)
588 {
589 context->setClearColor(red, green, blue, alpha);
590 }
591 }
592 catch(std::bad_alloc&)
593 {
594 return error(GL_OUT_OF_MEMORY);
595 }
596}
597
598void __stdcall glClearDepthf(GLclampf depth)
599{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000600 TRACE("(GLclampf depth = %f)", depth);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000601
602 try
603 {
604 gl::Context *context = gl::getContext();
605
606 if (context)
607 {
608 context->setClearDepth(depth);
609 }
610 }
611 catch(std::bad_alloc&)
612 {
613 return error(GL_OUT_OF_MEMORY);
614 }
615}
616
617void __stdcall glClearStencil(GLint s)
618{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000619 TRACE("(GLint s = %d)", s);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000620
621 try
622 {
623 gl::Context *context = gl::getContext();
624
625 if (context)
626 {
627 context->setClearStencil(s);
628 }
629 }
630 catch(std::bad_alloc&)
631 {
632 return error(GL_OUT_OF_MEMORY);
633 }
634}
635
636void __stdcall glColorMask(GLboolean red, GLboolean green, GLboolean blue, GLboolean alpha)
637{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000638 TRACE("(GLboolean red = %d, GLboolean green = %d, GLboolean blue = %d, GLboolean alpha = %d)",
639 red, green, blue, alpha);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000640
641 try
642 {
643 gl::Context *context = gl::getContext();
644
645 if (context)
646 {
647 context->colorMaskRed = red != GL_FALSE;
648 context->colorMaskGreen = green != GL_FALSE;
649 context->colorMaskBlue = blue != GL_FALSE;
650 context->colorMaskAlpha = alpha != GL_FALSE;
651 }
652 }
653 catch(std::bad_alloc&)
654 {
655 return error(GL_OUT_OF_MEMORY);
656 }
657}
658
659void __stdcall glCompileShader(GLuint shader)
660{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000661 TRACE("(GLuint shader = %d)", shader);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000662
663 try
664 {
665 gl::Context *context = gl::getContext();
666
667 if (context)
668 {
669 gl::Shader *shaderObject = context->getShader(shader);
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +0000670
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000671 if (!shaderObject)
672 {
673 return error(GL_INVALID_VALUE);
674 }
675
676 shaderObject->compile();
677 }
678 }
679 catch(std::bad_alloc&)
680 {
681 return error(GL_OUT_OF_MEMORY);
682 }
683}
684
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +0000685void __stdcall glCompressedTexImage2D(GLenum target, GLint level, GLenum internalformat, GLsizei width, GLsizei height,
686 GLint border, GLsizei imageSize, const GLvoid* data)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000687{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000688 TRACE("(GLenum target = 0x%X, GLint level = %d, GLenum internalformat = 0x%X, GLsizei width = %d, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +0000689 "GLsizei height = %d, GLint border = %d, GLsizei imageSize = %d, const GLvoid* data = 0x%0.8p)",
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000690 target, level, internalformat, width, height, border, imageSize, data);
691
692 try
693 {
daniel@transgaming.com41430492010-03-11 20:36:18 +0000694 if (target != GL_TEXTURE_2D && !es2dx::IsCubemapTextureTarget(target))
695 {
696 return error(GL_INVALID_ENUM);
697 }
698
699 if (level < 0 || level > gl::MAX_TEXTURE_LEVELS)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000700 {
701 return error(GL_INVALID_VALUE);
702 }
703
daniel@transgaming.com41430492010-03-11 20:36:18 +0000704 if (width < 0 || height < 0 || (level > 0 && !gl::isPow2(width)) || (level > 0 && !gl::isPow2(height)) || border != 0 || imageSize < 0)
705 {
706 return error(GL_INVALID_VALUE);
707 }
708
709 return error(GL_INVALID_ENUM); // ultimately we don't support compressed textures
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000710 }
711 catch(std::bad_alloc&)
712 {
713 return error(GL_OUT_OF_MEMORY);
714 }
715}
716
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +0000717void __stdcall glCompressedTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
718 GLenum format, GLsizei imageSize, const GLvoid* data)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000719{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000720 TRACE("(GLenum target = 0x%X, GLint level = %d, GLint xoffset = %d, GLint yoffset = %d, "
721 "GLsizei width = %d, GLsizei height = %d, GLenum format = 0x%X, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +0000722 "GLsizei imageSize = %d, const GLvoid* data = 0x%0.8p)",
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000723 target, level, xoffset, yoffset, width, height, format, imageSize, data);
724
725 try
726 {
daniel@transgaming.com41430492010-03-11 20:36:18 +0000727 if (target != GL_TEXTURE_2D && !es2dx::IsCubemapTextureTarget(target))
728 {
729 return error(GL_INVALID_ENUM);
730 }
731
732 if (level < 0 || level > gl::MAX_TEXTURE_LEVELS)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000733 {
734 return error(GL_INVALID_VALUE);
735 }
736
daniel@transgaming.com41430492010-03-11 20:36:18 +0000737 if (xoffset < 0 || yoffset < 0 || width < 0 || height < 0 || (level > 0 && !gl::isPow2(width)) || (level > 0 && !gl::isPow2(height)) || imageSize < 0)
738 {
739 return error(GL_INVALID_VALUE);
740 }
741
742 if (xoffset != 0 || yoffset != 0)
743 {
744 return error(GL_INVALID_OPERATION);
745 }
746
747 return error(GL_INVALID_OPERATION); // The texture being operated on is not a compressed texture.
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000748 }
749 catch(std::bad_alloc&)
750 {
751 return error(GL_OUT_OF_MEMORY);
752 }
753}
754
755void __stdcall glCopyTexImage2D(GLenum target, GLint level, GLenum internalformat, GLint x, GLint y, GLsizei width, GLsizei height, GLint border)
756{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000757 TRACE("(GLenum target = 0x%X, GLint level = %d, GLenum internalformat = 0x%X, "
758 "GLint x = %d, GLint y = %d, GLsizei width = %d, GLsizei height = %d, GLint border = %d)",
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000759 target, level, internalformat, x, y, width, height, border);
760
761 try
762 {
763 if (width < 0 || height < 0)
764 {
765 return error(GL_INVALID_VALUE);
766 }
767
768 UNIMPLEMENTED(); // FIXME
769 }
770 catch(std::bad_alloc&)
771 {
772 return error(GL_OUT_OF_MEMORY);
773 }
774}
775
776void __stdcall glCopyTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height)
777{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000778 TRACE("(GLenum target = 0x%X, GLint level = %d, GLint xoffset = %d, GLint yoffset = %d, "
779 "GLint x = %d, GLint y = %d, GLsizei width = %d, GLsizei height = %d)",
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000780 target, level, xoffset, yoffset, x, y, width, height);
781
782 try
783 {
784 if (width < 0 || height < 0)
785 {
786 return error(GL_INVALID_VALUE);
787 }
788
789 UNIMPLEMENTED(); // FIXME
790 }
791 catch(std::bad_alloc&)
792 {
793 return error(GL_OUT_OF_MEMORY);
794 }
795}
796
797GLuint __stdcall glCreateProgram(void)
798{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000799 TRACE("()");
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000800
801 try
802 {
803 gl::Context *context = gl::getContext();
804
805 if (context)
806 {
807 return context->createProgram();
808 }
809 }
810 catch(std::bad_alloc&)
811 {
812 return error(GL_OUT_OF_MEMORY, 0);
813 }
814
815 return 0;
816}
817
818GLuint __stdcall glCreateShader(GLenum type)
819{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000820 TRACE("(GLenum type = 0x%X)", type);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000821
822 try
823 {
824 gl::Context *context = gl::getContext();
825
826 if (context)
827 {
828 switch (type)
829 {
830 case GL_FRAGMENT_SHADER:
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +0000831 case GL_VERTEX_SHADER:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000832 return context->createShader(type);
833 default:
834 return error(GL_INVALID_ENUM, 0);
835 }
836 }
837 }
838 catch(std::bad_alloc&)
839 {
840 return error(GL_OUT_OF_MEMORY, 0);
841 }
842
843 return 0;
844}
845
846void __stdcall glCullFace(GLenum mode)
847{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000848 TRACE("(GLenum mode = 0x%X)", mode);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000849
850 try
851 {
852 switch (mode)
853 {
854 case GL_FRONT:
855 case GL_BACK:
856 case GL_FRONT_AND_BACK:
857 {
858 gl::Context *context = gl::getContext();
859
860 if (context)
861 {
862 context->cullMode = mode;
863 }
864 }
865 break;
866 default:
867 return error(GL_INVALID_ENUM);
868 }
869 }
870 catch(std::bad_alloc&)
871 {
872 return error(GL_OUT_OF_MEMORY);
873 }
874}
875
876void __stdcall glDeleteBuffers(GLsizei n, const GLuint* buffers)
877{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000878 TRACE("(GLsizei n = %d, const GLuint* buffers = 0x%0.8p)", n, buffers);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000879
880 try
881 {
882 if (n < 0)
883 {
884 return error(GL_INVALID_VALUE);
885 }
886
887 gl::Context *context = gl::getContext();
888
889 if (context)
890 {
891 for (int i = 0; i < n; i++)
892 {
893 context->deleteBuffer(buffers[i]);
894 }
895 }
896 }
897 catch(std::bad_alloc&)
898 {
899 return error(GL_OUT_OF_MEMORY);
900 }
901}
902
903void __stdcall glDeleteFramebuffers(GLsizei n, const GLuint* framebuffers)
904{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000905 TRACE("(GLsizei n = %d, const GLuint* framebuffers = 0x%0.8p)", n, framebuffers);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000906
907 try
908 {
909 if (n < 0)
910 {
911 return error(GL_INVALID_VALUE);
912 }
913
914 gl::Context *context = gl::getContext();
915
916 if (context)
917 {
918 for (int i = 0; i < n; i++)
919 {
920 if (framebuffers[i] != 0)
921 {
922 context->deleteFramebuffer(framebuffers[i]);
923 }
924 }
925 }
926 }
927 catch(std::bad_alloc&)
928 {
929 return error(GL_OUT_OF_MEMORY);
930 }
931}
932
933void __stdcall glDeleteProgram(GLuint program)
934{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000935 TRACE("(GLuint program = %d)", program);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000936
937 try
938 {
939 gl::Context *context = gl::getContext();
940
941 if (context)
942 {
943 context->deleteProgram(program);
944 }
945 }
946 catch(std::bad_alloc&)
947 {
948 return error(GL_OUT_OF_MEMORY);
949 }
950}
951
952void __stdcall glDeleteRenderbuffers(GLsizei n, const GLuint* renderbuffers)
953{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000954 TRACE("(GLsizei n = %d, const GLuint* renderbuffers = 0x%0.8p)", n, renderbuffers);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000955
956 try
957 {
958 if (n < 0)
959 {
960 return error(GL_INVALID_VALUE);
961 }
962
963 gl::Context *context = gl::getContext();
964
965 if (context)
966 {
daniel@transgaming.come2b22122010-03-11 19:22:14 +0000967 for (int i = 0; i < n; i++)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000968 {
969 context->deleteRenderbuffer(renderbuffers[i]);
970 }
971 }
972 }
973 catch(std::bad_alloc&)
974 {
975 return error(GL_OUT_OF_MEMORY);
976 }
977}
978
979void __stdcall glDeleteShader(GLuint shader)
980{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +0000981 TRACE("(GLuint shader = %d)", shader);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000982
983 try
984 {
985 gl::Context *context = gl::getContext();
986
987 if (context)
988 {
989 context->deleteShader(shader);
990 }
991 }
992 catch(std::bad_alloc&)
993 {
994 return error(GL_OUT_OF_MEMORY);
995 }
996}
997
998void __stdcall glDeleteTextures(GLsizei n, const GLuint* textures)
999{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001000 TRACE("(GLsizei n = %d, const GLuint* textures = 0x%0.8p)", n, textures);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001001
1002 try
1003 {
1004 if (n < 0)
1005 {
1006 return error(GL_INVALID_VALUE);
1007 }
1008
1009 gl::Context *context = gl::getContext();
1010
1011 if (context)
1012 {
1013 for (int i = 0; i < n; i++)
1014 {
1015 if (textures[i] != 0)
1016 {
1017 context->deleteTexture(textures[i]);
1018 }
1019 }
1020 }
1021 }
1022 catch(std::bad_alloc&)
1023 {
1024 return error(GL_OUT_OF_MEMORY);
1025 }
1026}
1027
1028void __stdcall glDepthFunc(GLenum func)
1029{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001030 TRACE("(GLenum func = 0x%X)", func);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001031
1032 try
1033 {
1034 switch (func)
1035 {
1036 case GL_NEVER:
1037 case GL_ALWAYS:
1038 case GL_LESS:
1039 case GL_LEQUAL:
1040 case GL_EQUAL:
1041 case GL_GREATER:
1042 case GL_GEQUAL:
1043 case GL_NOTEQUAL:
1044 break;
1045 default:
1046 return error(GL_INVALID_ENUM);
1047 }
1048
1049 gl::Context *context = gl::getContext();
1050
1051 if (context)
1052 {
1053 context->depthFunc = func;
1054 }
1055 }
1056 catch(std::bad_alloc&)
1057 {
1058 return error(GL_OUT_OF_MEMORY);
1059 }
1060}
1061
1062void __stdcall glDepthMask(GLboolean flag)
1063{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001064 TRACE("(GLboolean flag = %d)", flag);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001065
1066 try
1067 {
1068 gl::Context *context = gl::getContext();
1069
1070 if (context)
1071 {
1072 context->depthMask = flag != GL_FALSE;
1073 }
1074 }
1075 catch(std::bad_alloc&)
1076 {
1077 return error(GL_OUT_OF_MEMORY);
1078 }
1079}
1080
1081void __stdcall glDepthRangef(GLclampf zNear, GLclampf zFar)
1082{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001083 TRACE("(GLclampf zNear = %f, GLclampf zFar = %f)", zNear, zFar);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001084
1085 try
1086 {
1087 gl::Context *context = gl::getContext();
1088
1089 if (context)
1090 {
1091 context->zNear = zNear;
1092 context->zFar = zFar;
1093 }
1094 }
1095 catch(std::bad_alloc&)
1096 {
1097 return error(GL_OUT_OF_MEMORY);
1098 }
1099}
1100
1101void __stdcall glDetachShader(GLuint program, GLuint shader)
1102{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001103 TRACE("(GLuint program = %d, GLuint shader = %d)", program, shader);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001104
1105 try
1106 {
1107 gl::Context *context = gl::getContext();
1108
1109 if (context)
1110 {
daniel@transgaming.com73c2c2e2010-04-13 03:26:11 +00001111
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001112 gl::Program *programObject = context->getProgram(program);
1113 gl::Shader *shaderObject = context->getShader(shader);
daniel@transgaming.com73c2c2e2010-04-13 03:26:11 +00001114
1115 if (!programObject)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001116 {
daniel@transgaming.com73c2c2e2010-04-13 03:26:11 +00001117 gl::Shader *shaderByProgramHandle;
1118 shaderByProgramHandle = context->getShader(program);
1119 if (!shaderByProgramHandle)
1120 {
1121 return error(GL_INVALID_VALUE);
1122 }
1123 else
1124 {
1125 return error(GL_INVALID_OPERATION);
1126 }
1127 }
1128
1129 if (!shaderObject)
1130 {
1131 gl::Program *programByShaderHandle = context->getProgram(shader);
1132 if (!programByShaderHandle)
1133 {
1134 return error(GL_INVALID_VALUE);
1135 }
1136 else
1137 {
1138 return error(GL_INVALID_OPERATION);
1139 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001140 }
1141
1142 if (!programObject->detachShader(shaderObject))
1143 {
1144 return error(GL_INVALID_OPERATION);
1145 }
1146
1147 if (shaderObject->isDeletable())
1148 {
1149 context->deleteShader(shader);
1150 }
1151 }
1152 }
1153 catch(std::bad_alloc&)
1154 {
1155 return error(GL_OUT_OF_MEMORY);
1156 }
1157}
1158
1159void __stdcall glDisable(GLenum cap)
1160{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001161 TRACE("(GLenum cap = 0x%X)", cap);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001162
1163 try
1164 {
1165 gl::Context *context = gl::getContext();
1166
1167 if (context)
1168 {
1169 switch (cap)
1170 {
1171 case GL_CULL_FACE: context->cullFace = false; break;
1172 case GL_POLYGON_OFFSET_FILL: context->polygonOffsetFill = false; break;
1173 case GL_SAMPLE_ALPHA_TO_COVERAGE: context->sampleAlphaToCoverage = false; break;
1174 case GL_SAMPLE_COVERAGE: context->sampleCoverage = false; break;
1175 case GL_SCISSOR_TEST: context->scissorTest = false; break;
1176 case GL_STENCIL_TEST: context->stencilTest = false; break;
1177 case GL_DEPTH_TEST: context->depthTest = false; break;
1178 case GL_BLEND: context->blend = false; break;
1179 case GL_DITHER: context->dither = false; break;
1180 default:
1181 return error(GL_INVALID_ENUM);
1182 }
1183 }
1184 }
1185 catch(std::bad_alloc&)
1186 {
1187 return error(GL_OUT_OF_MEMORY);
1188 }
1189}
1190
1191void __stdcall glDisableVertexAttribArray(GLuint index)
1192{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001193 TRACE("(GLuint index = %d)", index);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001194
1195 try
1196 {
1197 if (index >= gl::MAX_VERTEX_ATTRIBS)
1198 {
1199 return error(GL_INVALID_VALUE);
1200 }
1201
1202 gl::Context *context = gl::getContext();
1203
1204 if (context)
1205 {
daniel@transgaming.com0f7aaf52010-03-11 19:41:38 +00001206 context->vertexAttribute[index].mEnabled = false;
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001207 }
1208 }
1209 catch(std::bad_alloc&)
1210 {
1211 return error(GL_OUT_OF_MEMORY);
1212 }
1213}
1214
1215void __stdcall glDrawArrays(GLenum mode, GLint first, GLsizei count)
1216{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001217 TRACE("(GLenum mode = 0x%X, GLint first = %d, GLsizei count = %d)", mode, first, count);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001218
1219 try
1220 {
1221 if (count < 0 || first < 0)
1222 {
1223 return error(GL_INVALID_VALUE);
1224 }
1225
1226 gl::Context *context = gl::getContext();
1227
1228 if (context)
1229 {
1230 context->drawArrays(mode, first, count);
1231 }
1232 }
1233 catch(std::bad_alloc&)
1234 {
1235 return error(GL_OUT_OF_MEMORY);
1236 }
1237}
1238
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00001239void __stdcall glDrawElements(GLenum mode, GLsizei count, GLenum type, const GLvoid* indices)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001240{
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00001241 TRACE("(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 +00001242 mode, count, type, indices);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001243
1244 try
1245 {
1246 if (count < 0)
1247 {
1248 return error(GL_INVALID_VALUE);
1249 }
1250
1251 switch (type)
1252 {
1253 case GL_UNSIGNED_BYTE:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001254 case GL_UNSIGNED_SHORT:
1255 break;
1256 default:
1257 return error(GL_INVALID_ENUM);
1258 }
1259
1260 gl::Context *context = gl::getContext();
1261
1262 if (context)
1263 {
1264 context->drawElements(mode, count, type, indices);
1265 }
1266 }
1267 catch(std::bad_alloc&)
1268 {
1269 return error(GL_OUT_OF_MEMORY);
1270 }
1271}
1272
1273void __stdcall glEnable(GLenum cap)
1274{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001275 TRACE("(GLenum cap = 0x%X)", cap);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001276
1277 try
1278 {
1279 gl::Context *context = gl::getContext();
1280
1281 if (context)
1282 {
1283 switch (cap)
1284 {
1285 case GL_CULL_FACE: context->cullFace = true; break;
1286 case GL_POLYGON_OFFSET_FILL: context->polygonOffsetFill = true; break;
1287 case GL_SAMPLE_ALPHA_TO_COVERAGE: context->sampleAlphaToCoverage = true; break;
1288 case GL_SAMPLE_COVERAGE: context->sampleCoverage = true; break;
1289 case GL_SCISSOR_TEST: context->scissorTest = true; break;
1290 case GL_STENCIL_TEST: context->stencilTest = true; break;
1291 case GL_DEPTH_TEST: context->depthTest = true; break;
1292 case GL_BLEND: context->blend = true; break;
1293 case GL_DITHER: context->dither = true; break;
1294 default:
1295 return error(GL_INVALID_ENUM);
1296 }
1297 }
1298 }
1299 catch(std::bad_alloc&)
1300 {
1301 return error(GL_OUT_OF_MEMORY);
1302 }
1303}
1304
1305void __stdcall glEnableVertexAttribArray(GLuint index)
1306{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001307 TRACE("(GLuint index = %d)", index);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001308
1309 try
1310 {
1311 if (index >= gl::MAX_VERTEX_ATTRIBS)
1312 {
1313 return error(GL_INVALID_VALUE);
1314 }
1315
1316 gl::Context *context = gl::getContext();
1317
1318 if (context)
1319 {
daniel@transgaming.com0f7aaf52010-03-11 19:41:38 +00001320 context->vertexAttribute[index].mEnabled = true;
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001321 }
1322 }
1323 catch(std::bad_alloc&)
1324 {
1325 return error(GL_OUT_OF_MEMORY);
1326 }
1327}
1328
1329void __stdcall glFinish(void)
1330{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001331 TRACE("()");
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001332
1333 try
1334 {
1335 gl::Context *context = gl::getContext();
1336
1337 if (context)
1338 {
1339 context->finish();
1340 }
1341 }
1342 catch(std::bad_alloc&)
1343 {
1344 return error(GL_OUT_OF_MEMORY);
1345 }
1346}
1347
1348void __stdcall glFlush(void)
1349{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001350 TRACE("()");
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001351
1352 try
1353 {
1354 gl::Context *context = gl::getContext();
1355
1356 if (context)
1357 {
1358 context->flush();
1359 }
1360 }
1361 catch(std::bad_alloc&)
1362 {
1363 return error(GL_OUT_OF_MEMORY);
1364 }
1365}
1366
1367void __stdcall glFramebufferRenderbuffer(GLenum target, GLenum attachment, GLenum renderbuffertarget, GLuint renderbuffer)
1368{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001369 TRACE("(GLenum target = 0x%X, GLenum attachment = 0x%X, GLenum renderbuffertarget = 0x%X, "
1370 "GLuint renderbuffer = %d)", target, attachment, renderbuffertarget, renderbuffer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001371
1372 try
1373 {
1374 if (target != GL_FRAMEBUFFER || renderbuffertarget != GL_RENDERBUFFER)
1375 {
1376 return error(GL_INVALID_ENUM);
1377 }
1378
1379 gl::Context *context = gl::getContext();
1380
1381 if (context)
1382 {
1383 gl::Framebuffer *framebuffer = context->getFramebuffer();
1384
1385 if (context->framebuffer == 0 || !framebuffer)
1386 {
1387 return error(GL_INVALID_OPERATION);
1388 }
1389
1390 switch (attachment)
1391 {
1392 case GL_COLOR_ATTACHMENT0:
1393 framebuffer->setColorbuffer(GL_RENDERBUFFER, renderbuffer);
1394 break;
1395 case GL_DEPTH_ATTACHMENT:
1396 framebuffer->setDepthbuffer(GL_RENDERBUFFER, renderbuffer);
1397 break;
1398 case GL_STENCIL_ATTACHMENT:
1399 framebuffer->setStencilbuffer(GL_RENDERBUFFER, renderbuffer);
1400 break;
1401 default:
1402 return error(GL_INVALID_ENUM);
1403 }
1404 }
1405 }
1406 catch(std::bad_alloc&)
1407 {
1408 return error(GL_OUT_OF_MEMORY);
1409 }
1410}
1411
1412void __stdcall glFramebufferTexture2D(GLenum target, GLenum attachment, GLenum textarget, GLuint texture, GLint level)
1413{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001414 TRACE("(GLenum target = 0x%X, GLenum attachment = 0x%X, GLenum textarget = 0x%X, "
1415 "GLuint texture = %d, GLint level = %d)", target, attachment, textarget, texture, level);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001416
1417 try
1418 {
1419 if (target != GL_FRAMEBUFFER)
1420 {
1421 return error(GL_INVALID_ENUM);
1422 }
1423
1424 switch (attachment)
1425 {
1426 case GL_COLOR_ATTACHMENT0:
1427 break;
1428 default:
1429 return error(GL_INVALID_ENUM);
1430 }
1431
1432 gl::Context *context = gl::getContext();
1433
1434 if (context)
1435 {
1436 if (texture)
1437 {
1438 switch (textarget)
1439 {
1440 case GL_TEXTURE_2D:
1441 if (!context->getTexture2D())
1442 {
1443 return error(GL_INVALID_OPERATION);
1444 }
1445 break;
1446 case GL_TEXTURE_CUBE_MAP_POSITIVE_X:
1447 UNIMPLEMENTED(); // FIXME
1448 break;
1449 case GL_TEXTURE_CUBE_MAP_NEGATIVE_X:
1450 UNIMPLEMENTED(); // FIXME
1451 break;
1452 case GL_TEXTURE_CUBE_MAP_POSITIVE_Y:
1453 UNIMPLEMENTED(); // FIXME
1454 break;
1455 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y:
1456 UNIMPLEMENTED(); // FIXME
1457 break;
1458 case GL_TEXTURE_CUBE_MAP_POSITIVE_Z:
1459 UNIMPLEMENTED(); // FIXME
1460 break;
1461 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z:
1462 UNIMPLEMENTED(); // FIXME
1463 break;
1464 default:
1465 return error(GL_INVALID_ENUM);
1466 }
1467
1468 if (level != 0)
1469 {
1470 return error(GL_INVALID_VALUE);
1471 }
1472 }
1473
1474 gl::Framebuffer *framebuffer = context->getFramebuffer();
1475
1476 if (context->framebuffer == 0 || !framebuffer)
1477 {
1478 return error(GL_INVALID_OPERATION);
1479 }
1480
1481 framebuffer->setColorbuffer(GL_TEXTURE, texture);
1482 }
1483 }
1484 catch(std::bad_alloc&)
1485 {
1486 return error(GL_OUT_OF_MEMORY);
1487 }
1488}
1489
1490void __stdcall glFrontFace(GLenum mode)
1491{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001492 TRACE("(GLenum mode = 0x%X)", mode);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001493
1494 try
1495 {
1496 switch (mode)
1497 {
1498 case GL_CW:
1499 case GL_CCW:
1500 {
1501 gl::Context *context = gl::getContext();
1502
1503 if (context)
1504 {
1505 context->frontFace = mode;
1506 }
1507 }
1508 break;
1509 default:
1510 return error(GL_INVALID_ENUM);
1511 }
1512 }
1513 catch(std::bad_alloc&)
1514 {
1515 return error(GL_OUT_OF_MEMORY);
1516 }
1517}
1518
1519void __stdcall glGenBuffers(GLsizei n, GLuint* buffers)
1520{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001521 TRACE("(GLsizei n = %d, GLuint* buffers = 0x%0.8p)", n, buffers);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001522
1523 try
1524 {
1525 if (n < 0)
1526 {
1527 return error(GL_INVALID_VALUE);
1528 }
1529
1530 gl::Context *context = gl::getContext();
1531
1532 if (context)
1533 {
1534 for (int i = 0; i < n; i++)
1535 {
1536 buffers[i] = context->createBuffer();
1537 }
1538 }
1539 }
1540 catch(std::bad_alloc&)
1541 {
1542 return error(GL_OUT_OF_MEMORY);
1543 }
1544}
1545
1546void __stdcall glGenerateMipmap(GLenum target)
1547{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001548 TRACE("(GLenum target = 0x%X)", target);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001549
1550 try
1551 {
1552 UNIMPLEMENTED(); // FIXME
1553 }
1554 catch(std::bad_alloc&)
1555 {
1556 return error(GL_OUT_OF_MEMORY);
1557 }
1558}
1559
1560void __stdcall glGenFramebuffers(GLsizei n, GLuint* framebuffers)
1561{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001562 TRACE("(GLsizei n = %d, GLuint* framebuffers = 0x%0.8p)", n, framebuffers);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001563
1564 try
1565 {
1566 if (n < 0)
1567 {
1568 return error(GL_INVALID_VALUE);
1569 }
1570
1571 gl::Context *context = gl::getContext();
1572
1573 if (context)
1574 {
1575 for (int i = 0; i < n; i++)
1576 {
1577 framebuffers[i] = context->createFramebuffer();
1578 }
1579 }
1580 }
1581 catch(std::bad_alloc&)
1582 {
1583 return error(GL_OUT_OF_MEMORY);
1584 }
1585}
1586
1587void __stdcall glGenRenderbuffers(GLsizei n, GLuint* renderbuffers)
1588{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001589 TRACE("(GLsizei n = %d, GLuint* renderbuffers = 0x%0.8p)", n, renderbuffers);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001590
1591 try
1592 {
1593 if (n < 0)
1594 {
1595 return error(GL_INVALID_VALUE);
1596 }
1597
1598 gl::Context *context = gl::getContext();
1599
1600 if (context)
1601 {
1602 for (int i = 0; i < n; i++)
1603 {
1604 renderbuffers[i] = context->createRenderbuffer();
1605 }
1606 }
1607 }
1608 catch(std::bad_alloc&)
1609 {
1610 return error(GL_OUT_OF_MEMORY);
1611 }
1612}
1613
1614void __stdcall glGenTextures(GLsizei n, GLuint* textures)
1615{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001616 TRACE("(GLsizei n = %d, GLuint* textures = 0x%0.8p)", n, textures);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001617
1618 try
1619 {
1620 if (n < 0)
1621 {
1622 return error(GL_INVALID_VALUE);
1623 }
1624
1625 gl::Context *context = gl::getContext();
1626
1627 if (context)
1628 {
1629 for (int i = 0; i < n; i++)
1630 {
1631 textures[i] = context->createTexture();
1632 }
1633 }
1634 }
1635 catch(std::bad_alloc&)
1636 {
1637 return error(GL_OUT_OF_MEMORY);
1638 }
1639}
1640
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00001641void __stdcall glGetActiveAttrib(GLuint program, GLuint index, GLsizei bufsize, GLsizei* length, GLint* size, GLenum* type, GLchar* name)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001642{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001643 TRACE("(GLuint program = %d, GLuint index = %d, GLsizei bufsize = %d, GLsizei* length = 0x%0.8p, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00001644 "GLint* size = 0x%0.8p, GLenum* type = %0.8p, GLchar* name = %0.8p)",
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001645 program, index, bufsize, length, size, type, name);
1646
1647 try
1648 {
1649 if (bufsize < 0)
1650 {
1651 return error(GL_INVALID_VALUE);
1652 }
1653
1654 UNIMPLEMENTED(); // FIXME
1655 }
1656 catch(std::bad_alloc&)
1657 {
1658 return error(GL_OUT_OF_MEMORY);
1659 }
1660}
1661
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00001662void __stdcall glGetActiveUniform(GLuint program, GLuint index, GLsizei bufsize, GLsizei* length, GLint* size, GLenum* type, GLchar* name)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001663{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001664 TRACE("(GLuint program = %d, GLuint index = %d, GLsizei bufsize = %d, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00001665 "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 +00001666 program, index, bufsize, length, size, type, name);
1667
1668 try
1669 {
1670 if (bufsize < 0)
1671 {
1672 return error(GL_INVALID_VALUE);
1673 }
1674
1675 UNIMPLEMENTED(); // FIXME
1676 }
1677 catch(std::bad_alloc&)
1678 {
1679 return error(GL_OUT_OF_MEMORY);
1680 }
1681}
1682
1683void __stdcall glGetAttachedShaders(GLuint program, GLsizei maxcount, GLsizei* count, GLuint* shaders)
1684{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001685 TRACE("(GLuint program = %d, GLsizei maxcount = %d, GLsizei* count = 0x%0.8p, GLuint* shaders = 0x%0.8p)",
1686 program, maxcount, count, shaders);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001687
1688 try
1689 {
1690 if (maxcount < 0)
1691 {
1692 return error(GL_INVALID_VALUE);
1693 }
1694
daniel@transgaming.com6c785212010-03-30 03:36:17 +00001695 gl::Context *context = gl::getContext();
1696
1697 if (context)
1698 {
1699 gl::Program *programObject = context->getProgram(program);
1700
1701 if (!programObject)
1702 {
1703 return error(GL_INVALID_VALUE);
1704 }
1705
1706 return programObject->getAttachedShaders(maxcount, count, shaders);
1707 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001708 }
1709 catch(std::bad_alloc&)
1710 {
1711 return error(GL_OUT_OF_MEMORY);
1712 }
1713}
1714
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00001715int __stdcall glGetAttribLocation(GLuint program, const GLchar* name)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001716{
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00001717 TRACE("(GLuint program = %d, const GLchar* name = %s)", program, name);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001718
1719 try
1720 {
1721 gl::Context *context = gl::getContext();
1722
1723 if (context)
1724 {
1725 gl::Program *programObject = context->getProgram(program);
1726
1727 if (!programObject)
1728 {
1729 return error(GL_INVALID_VALUE, -1);
1730 }
1731
1732 return programObject->getAttributeLocation(name);
1733 }
1734 }
1735 catch(std::bad_alloc&)
1736 {
1737 return error(GL_OUT_OF_MEMORY, -1);
1738 }
1739
1740 return -1;
1741}
1742
1743void __stdcall glGetBooleanv(GLenum pname, GLboolean* params)
1744{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001745 TRACE("(GLenum pname = 0x%X, GLboolean* params = 0x%0.8p)", pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001746
1747 try
1748 {
daniel@transgaming.com777f2672010-04-07 03:25:16 +00001749 gl::Context *context = gl::getContext();
1750
1751 if (context)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001752 {
daniel@transgaming.com777f2672010-04-07 03:25:16 +00001753 if (!(context->getBooleanv(pname, params)))
1754 {
1755 GLenum nativeType;
1756 unsigned int numParams = 0;
1757 if (!context->getQueryParameterInfo(pname, &nativeType, &numParams))
1758 return error(GL_INVALID_ENUM);
1759
1760 if (numParams == 0)
1761 return; // it is known that the pname is valid, but there are no parameters to return
1762
1763 if (nativeType == GL_FLOAT)
1764 {
1765 GLfloat *floatParams = NULL;
1766 floatParams = new GLfloat[numParams];
1767
1768 context->getFloatv(pname, floatParams);
1769
1770 for (unsigned int i = 0; i < numParams; ++i)
1771 {
1772 if (floatParams[i] == 0.0f)
1773 params[i] = GL_FALSE;
1774 else
1775 params[i] = GL_TRUE;
1776 }
1777
1778 delete [] floatParams;
1779 }
1780 else if (nativeType == GL_INT)
1781 {
1782 GLint *intParams = NULL;
1783 intParams = new GLint[numParams];
1784
1785 context->getIntegerv(pname, intParams);
1786
1787 for (unsigned int i = 0; i < numParams; ++i)
1788 {
1789 if (intParams[i] == 0)
1790 params[i] = GL_FALSE;
1791 else
1792 params[i] = GL_TRUE;
1793 }
1794
1795 delete [] intParams;
1796 }
1797 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001798 }
1799 }
1800 catch(std::bad_alloc&)
1801 {
1802 return error(GL_OUT_OF_MEMORY);
1803 }
1804}
1805
1806void __stdcall glGetBufferParameteriv(GLenum target, GLenum pname, GLint* params)
1807{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001808 TRACE("(GLenum target = 0x%X, GLenum pname = 0x%X, GLint* params = 0x%0.8p)", target, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001809
1810 try
1811 {
1812 UNIMPLEMENTED(); // FIXME
1813 }
1814 catch(std::bad_alloc&)
1815 {
1816 return error(GL_OUT_OF_MEMORY);
1817 }
1818}
1819
1820GLenum __stdcall glGetError(void)
1821{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001822 TRACE("()");
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001823
1824 gl::Context *context = gl::getContext();
1825
1826 if (context)
1827 {
1828 return context->getError();
1829 }
1830
1831 return GL_NO_ERROR;
1832}
1833
1834void __stdcall glGetFloatv(GLenum pname, GLfloat* params)
1835{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001836 TRACE("(GLenum pname = 0x%X, GLfloat* params = 0x%0.8p)", pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001837
1838 try
1839 {
daniel@transgaming.com32e58cd2010-03-24 09:44:10 +00001840 gl::Context *context = gl::getContext();
1841
1842 if (context)
1843 {
daniel@transgaming.com777f2672010-04-07 03:25:16 +00001844 if (!(context->getFloatv(pname, params)))
daniel@transgaming.com32e58cd2010-03-24 09:44:10 +00001845 {
daniel@transgaming.com777f2672010-04-07 03:25:16 +00001846 GLenum nativeType;
1847 unsigned int numParams = 0;
1848 if (!context->getQueryParameterInfo(pname, &nativeType, &numParams))
1849 return error(GL_INVALID_ENUM);
1850
1851 if (numParams == 0)
1852 return; // it is known that the pname is valid, but that there are no parameters to return.
1853
1854 if (nativeType == GL_BOOL)
1855 {
1856 GLboolean *boolParams = NULL;
1857 boolParams = new GLboolean[numParams];
1858
1859 context->getBooleanv(pname, boolParams);
1860
1861 for (unsigned int i = 0; i < numParams; ++i)
1862 {
1863 if (boolParams[i] == GL_FALSE)
1864 params[i] = 0.0f;
1865 else
1866 params[i] = 1.0f;
1867 }
1868
1869 delete [] boolParams;
1870 }
1871 else if (nativeType == GL_INT)
1872 {
1873 GLint *intParams = NULL;
1874 intParams = new GLint[numParams];
1875
1876 context->getIntegerv(pname, intParams);
1877
1878 for (unsigned int i = 0; i < numParams; ++i)
1879 {
1880 params[i] = (GLfloat)intParams[i];
1881 }
1882
1883 delete [] intParams;
1884 }
daniel@transgaming.com32e58cd2010-03-24 09:44:10 +00001885 }
1886 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001887 }
1888 catch(std::bad_alloc&)
1889 {
1890 return error(GL_OUT_OF_MEMORY);
1891 }
1892}
1893
1894void __stdcall glGetFramebufferAttachmentParameteriv(GLenum target, GLenum attachment, GLenum pname, GLint* params)
1895{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001896 TRACE("(GLenum target = 0x%X, GLenum attachment = 0x%X, GLenum pname = 0x%X, GLint* params = 0x%0.8p)",
1897 target, attachment, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001898
1899 try
1900 {
1901 gl::Context *context = gl::getContext();
1902
1903 if (context)
1904 {
1905 if (context->framebuffer == 0)
1906 {
1907 return error(GL_INVALID_OPERATION);
1908 }
1909
1910 UNIMPLEMENTED(); // FIXME
1911 }
1912 }
1913 catch(std::bad_alloc&)
1914 {
1915 return error(GL_OUT_OF_MEMORY);
1916 }
1917}
1918
1919void __stdcall glGetIntegerv(GLenum pname, GLint* params)
1920{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001921 TRACE("(GLenum pname = 0x%X, GLint* params = 0x%0.8p)", pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001922
1923 try
1924 {
1925 gl::Context *context = gl::getContext();
1926
1927 if (context)
1928 {
daniel@transgaming.com777f2672010-04-07 03:25:16 +00001929 if (!(context->getIntegerv(pname, params)))
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001930 {
daniel@transgaming.com777f2672010-04-07 03:25:16 +00001931 GLenum nativeType;
1932 unsigned int numParams = 0;
1933 if (!context->getQueryParameterInfo(pname, &nativeType, &numParams))
1934 return error(GL_INVALID_ENUM);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001935
daniel@transgaming.com777f2672010-04-07 03:25:16 +00001936 if (numParams == 0)
1937 return; // it is known that pname is valid, but there are no parameters to return
1938
1939 if (nativeType == GL_BOOL)
1940 {
1941 GLboolean *boolParams = NULL;
1942 boolParams = new GLboolean[numParams];
1943
1944 context->getBooleanv(pname, boolParams);
1945
1946 for (unsigned int i = 0; i < numParams; ++i)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001947 {
daniel@transgaming.com777f2672010-04-07 03:25:16 +00001948 if (boolParams[i] == GL_FALSE)
1949 params[i] = 0;
1950 else
1951 params[i] = 1;
1952 }
1953
1954 delete [] boolParams;
1955 }
1956 else if (nativeType == GL_FLOAT)
1957 {
1958 GLfloat *floatParams = NULL;
1959 floatParams = new GLfloat[numParams];
1960
1961 context->getFloatv(pname, floatParams);
1962
1963 for (unsigned int i = 0; i < numParams; ++i)
1964 {
1965 if (pname == GL_DEPTH_RANGE || pname == GL_COLOR_CLEAR_VALUE || pname == GL_DEPTH_CLEAR_VALUE)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001966 {
daniel@transgaming.com777f2672010-04-07 03:25:16 +00001967 params[i] = (GLint)(((GLfloat)(0xFFFFFFFF) * floatParams[i] - 1.0f) / 2.0f);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001968 }
daniel@transgaming.com777f2672010-04-07 03:25:16 +00001969 else
1970 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 +00001971 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001972
daniel@transgaming.com777f2672010-04-07 03:25:16 +00001973 delete [] floatParams;
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001974 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001975 }
1976 }
1977 }
1978 catch(std::bad_alloc&)
1979 {
1980 return error(GL_OUT_OF_MEMORY);
1981 }
1982}
1983
1984void __stdcall glGetProgramiv(GLuint program, GLenum pname, GLint* params)
1985{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00001986 TRACE("(GLuint program = %d, GLenum pname = %d, GLint* params = 0x%0.8p)", program, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001987
1988 try
1989 {
1990 gl::Context *context = gl::getContext();
1991
1992 if (context)
1993 {
1994 gl::Program *programObject = context->getProgram(program);
1995
1996 if (!programObject)
1997 {
1998 return error(GL_INVALID_VALUE);
1999 }
2000
2001 switch (pname)
2002 {
2003 case GL_DELETE_STATUS:
daniel@transgaming.comcba50572010-03-28 19:36:09 +00002004 *params = programObject->isFlaggedForDeletion();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002005 return;
2006 case GL_LINK_STATUS:
2007 *params = programObject->isLinked();
2008 return;
2009 case GL_VALIDATE_STATUS:
2010 UNIMPLEMENTED(); // FIXME
2011 *params = GL_TRUE;
2012 return;
2013 case GL_INFO_LOG_LENGTH:
daniel@transgaming.comcba50572010-03-28 19:36:09 +00002014 *params = programObject->getInfoLogLength();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002015 return;
2016 case GL_ATTACHED_SHADERS:
daniel@transgaming.comcba50572010-03-28 19:36:09 +00002017 *params = programObject->getAttachedShadersCount();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002018 return;
2019 case GL_ACTIVE_ATTRIBUTES:
2020 UNIMPLEMENTED(); // FIXME
2021 *params = 0;
2022 return;
2023 case GL_ACTIVE_ATTRIBUTE_MAX_LENGTH:
2024 UNIMPLEMENTED(); // FIXME
2025 *params = 0;
2026 return;
2027 case GL_ACTIVE_UNIFORMS:
2028 UNIMPLEMENTED(); // FIXME
2029 *params = 0;
2030 return;
2031 case GL_ACTIVE_UNIFORM_MAX_LENGTH:
2032 UNIMPLEMENTED(); // FIXME
2033 *params = 0;
2034 return;
2035 default:
2036 return error(GL_INVALID_ENUM);
2037 }
2038 }
2039 }
2040 catch(std::bad_alloc&)
2041 {
2042 return error(GL_OUT_OF_MEMORY);
2043 }
2044}
2045
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002046void __stdcall glGetProgramInfoLog(GLuint program, GLsizei bufsize, GLsizei* length, GLchar* infolog)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002047{
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002048 TRACE("(GLuint program = %d, GLsizei bufsize = %d, GLsizei* length = 0x%0.8p, GLchar* infolog = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002049 program, bufsize, length, infolog);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002050
2051 try
2052 {
2053 if (bufsize < 0)
2054 {
2055 return error(GL_INVALID_VALUE);
2056 }
2057
daniel@transgaming.comcba50572010-03-28 19:36:09 +00002058 gl::Context *context = gl::getContext();
2059
2060 if (context)
2061 {
2062 gl::Program *programObject = context->getProgram(program);
2063
2064 if (!programObject)
2065 {
2066 return error(GL_INVALID_VALUE);
2067 }
2068
2069 programObject->getInfoLog(bufsize, length, infolog);
2070 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002071 }
2072 catch(std::bad_alloc&)
2073 {
2074 return error(GL_OUT_OF_MEMORY);
2075 }
2076}
2077
2078void __stdcall glGetRenderbufferParameteriv(GLenum target, GLenum pname, GLint* params)
2079{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002080 TRACE("(GLenum target = 0x%X, GLenum pname = 0x%X, GLint* params = 0x%0.8p)", target, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002081
2082 try
2083 {
2084 UNIMPLEMENTED(); // FIXME
2085 }
2086 catch(std::bad_alloc&)
2087 {
2088 return error(GL_OUT_OF_MEMORY);
2089 }
2090}
2091
2092void __stdcall glGetShaderiv(GLuint shader, GLenum pname, GLint* params)
2093{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002094 TRACE("(GLuint shader = %d, GLenum pname = %d, GLint* params = 0x%0.8p)", shader, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002095
2096 try
2097 {
2098 gl::Context *context = gl::getContext();
2099
2100 if (context)
2101 {
2102 gl::Shader *shaderObject = context->getShader(shader);
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00002103
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002104 if (!shaderObject)
2105 {
2106 return error(GL_INVALID_VALUE);
2107 }
2108
2109 switch (pname)
2110 {
2111 case GL_SHADER_TYPE:
2112 *params = shaderObject->getType();
2113 return;
2114 case GL_DELETE_STATUS:
daniel@transgaming.comcba50572010-03-28 19:36:09 +00002115 *params = shaderObject->isFlaggedForDeletion();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002116 return;
2117 case GL_COMPILE_STATUS:
2118 *params = shaderObject->isCompiled() ? GL_TRUE : GL_FALSE;
2119 return;
2120 case GL_INFO_LOG_LENGTH:
daniel@transgaming.comcba50572010-03-28 19:36:09 +00002121 *params = shaderObject->getInfoLogLength();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002122 return;
2123 case GL_SHADER_SOURCE_LENGTH:
daniel@transgaming.comcba50572010-03-28 19:36:09 +00002124 *params = shaderObject->getSourceLength();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002125 return;
2126 default:
2127 return error(GL_INVALID_ENUM);
2128 }
2129 }
2130 }
2131 catch(std::bad_alloc&)
2132 {
2133 return error(GL_OUT_OF_MEMORY);
2134 }
2135}
2136
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002137void __stdcall glGetShaderInfoLog(GLuint shader, GLsizei bufsize, GLsizei* length, GLchar* infolog)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002138{
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002139 TRACE("(GLuint shader = %d, GLsizei bufsize = %d, GLsizei* length = 0x%0.8p, GLchar* infolog = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002140 shader, bufsize, length, infolog);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002141
2142 try
2143 {
2144 if (bufsize < 0)
2145 {
2146 return error(GL_INVALID_VALUE);
2147 }
2148
daniel@transgaming.comcba50572010-03-28 19:36:09 +00002149 gl::Context *context = gl::getContext();
2150
2151 if (context)
2152 {
2153 gl::Shader *shaderObject = context->getShader(shader);
2154
2155 if (!shaderObject)
2156 {
2157 return error(GL_INVALID_VALUE);
2158 }
2159
2160 shaderObject->getInfoLog(bufsize, length, infolog);
2161 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002162 }
2163 catch(std::bad_alloc&)
2164 {
2165 return error(GL_OUT_OF_MEMORY);
2166 }
2167}
2168
2169void __stdcall glGetShaderPrecisionFormat(GLenum shadertype, GLenum precisiontype, GLint* range, GLint* precision)
2170{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002171 TRACE("(GLenum shadertype = 0x%X, GLenum precisiontype = 0x%X, GLint* range = 0x%0.8p, GLint* precision = 0x%0.8p)",
2172 shadertype, precisiontype, range, precision);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002173
2174 try
2175 {
daniel@transgaming.com6c785212010-03-30 03:36:17 +00002176 switch (shadertype)
2177 {
2178 case GL_VERTEX_SHADER:
2179 case GL_FRAGMENT_SHADER:
2180 break;
2181 default:
2182 return error(GL_INVALID_ENUM);
2183 }
2184
2185 switch (precisiontype)
2186 {
2187 case GL_LOW_FLOAT:
2188 case GL_MEDIUM_FLOAT:
2189 case GL_HIGH_FLOAT:
2190 // Assume IEEE 754 precision
2191 range[0] = 127;
2192 range[1] = 127;
2193 precision[0] = 23;
2194 precision[1] = 23;
2195 break;
2196 case GL_LOW_INT:
2197 case GL_MEDIUM_INT:
2198 case GL_HIGH_INT:
2199 // Some (most) hardware only supports single-precision floating-point numbers,
2200 // which can accurately represent integers up to +/-16777216
2201 range[0] = 24;
2202 range[1] = 24;
2203 precision[0] = 0;
2204 precision[1] = 0;
2205 break;
2206 default:
2207 return error(GL_INVALID_ENUM);
2208 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002209 }
2210 catch(std::bad_alloc&)
2211 {
2212 return error(GL_OUT_OF_MEMORY);
2213 }
2214}
2215
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002216void __stdcall glGetShaderSource(GLuint shader, GLsizei bufsize, GLsizei* length, GLchar* source)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002217{
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002218 TRACE("(GLuint shader = %d, GLsizei bufsize = %d, GLsizei* length = 0x%0.8p, GLchar* source = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002219 shader, bufsize, length, source);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002220
2221 try
2222 {
2223 if (bufsize < 0)
2224 {
2225 return error(GL_INVALID_VALUE);
2226 }
2227
daniel@transgaming.comcba50572010-03-28 19:36:09 +00002228 gl::Context *context = gl::getContext();
2229
2230 if (context)
2231 {
2232 gl::Shader *shaderObject = context->getShader(shader);
2233
2234 if (!shaderObject)
2235 {
daniel@transgaming.com41187f12010-04-01 13:39:29 +00002236 return error(GL_INVALID_OPERATION);
daniel@transgaming.comcba50572010-03-28 19:36:09 +00002237 }
2238
2239 shaderObject->getSource(bufsize, length, source);
2240 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002241 }
2242 catch(std::bad_alloc&)
2243 {
2244 return error(GL_OUT_OF_MEMORY);
2245 }
2246}
2247
2248const GLubyte* __stdcall glGetString(GLenum name)
2249{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002250 TRACE("(GLenum name = 0x%X)", name);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002251
2252 try
2253 {
2254 switch (name)
2255 {
2256 case GL_VENDOR:
2257 return (GLubyte*)"TransGaming Inc.";
2258 case GL_RENDERER:
2259 return (GLubyte*)"ANGLE";
2260 case GL_VERSION:
2261 return (GLubyte*)"OpenGL ES 2.0 (git-devel "__DATE__ " " __TIME__")";
2262 case GL_SHADING_LANGUAGE_VERSION:
2263 return (GLubyte*)"OpenGL ES GLSL ES 1.00 (git-devel "__DATE__ " " __TIME__")";
2264 case GL_EXTENSIONS:
2265 return (GLubyte*)"";
2266 default:
2267 return error(GL_INVALID_ENUM, (GLubyte*)NULL);
2268 }
2269 }
2270 catch(std::bad_alloc&)
2271 {
2272 return error(GL_OUT_OF_MEMORY, (GLubyte*)NULL);
2273 }
2274
2275 return NULL;
2276}
2277
2278void __stdcall glGetTexParameterfv(GLenum target, GLenum pname, GLfloat* params)
2279{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002280 TRACE("(GLenum target = 0x%X, GLenum pname = 0x%X, GLfloat* params = 0x%0.8p)", target, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002281
2282 try
2283 {
2284 UNIMPLEMENTED(); // FIXME
2285 }
2286 catch(std::bad_alloc&)
2287 {
2288 return error(GL_OUT_OF_MEMORY);
2289 }
2290}
2291
2292void __stdcall glGetTexParameteriv(GLenum target, GLenum pname, GLint* params)
2293{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002294 TRACE("(GLenum target = 0x%X, GLenum pname = 0x%X, GLint* params = 0x%0.8p)", target, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002295
2296 try
2297 {
2298 UNIMPLEMENTED(); // FIXME
2299 }
2300 catch(std::bad_alloc&)
2301 {
2302 return error(GL_OUT_OF_MEMORY);
2303 }
2304}
2305
2306void __stdcall glGetUniformfv(GLuint program, GLint location, GLfloat* params)
2307{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002308 TRACE("(GLuint program = %d, GLint location = %d, GLfloat* params = 0x%0.8p)", program, location, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002309
2310 try
2311 {
daniel@transgaming.combb3d9d02010-04-13 03:26:06 +00002312 gl::Context *context = gl::getContext();
2313
2314 if (context)
2315 {
2316 if (program == 0)
2317 {
2318 return error(GL_INVALID_VALUE);
2319 }
2320
2321 gl::Program *programObject = context->getProgram(program);
2322
2323 if (!programObject || !programObject->isLinked())
2324 {
2325 return error(GL_INVALID_OPERATION);
2326 }
2327
2328 if (!programObject->getUniformfv(location, params))
2329 {
2330 return error(GL_INVALID_OPERATION);
2331 }
2332 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002333 }
2334 catch(std::bad_alloc&)
2335 {
2336 return error(GL_OUT_OF_MEMORY);
2337 }
2338}
2339
2340void __stdcall glGetUniformiv(GLuint program, GLint location, GLint* params)
2341{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002342 TRACE("(GLuint program = %d, GLint location = %d, GLint* params = 0x%0.8p)", program, location, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002343
2344 try
2345 {
daniel@transgaming.combb3d9d02010-04-13 03:26:06 +00002346 gl::Context *context = gl::getContext();
2347
2348 if (context)
2349 {
2350 if (program == 0)
2351 {
2352 return error(GL_INVALID_VALUE);
2353 }
2354
2355 gl::Program *programObject = context->getProgram(program);
2356
2357 if (!programObject || !programObject->isLinked())
2358 {
2359 return error(GL_INVALID_OPERATION);
2360 }
2361
2362 if (!programObject)
2363 {
2364 return error(GL_INVALID_OPERATION);
2365 }
2366
2367 if (!programObject->getUniformiv(location, params))
2368 {
2369 return error(GL_INVALID_OPERATION);
2370 }
2371 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002372 }
2373 catch(std::bad_alloc&)
2374 {
2375 return error(GL_OUT_OF_MEMORY);
2376 }
2377}
2378
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002379int __stdcall glGetUniformLocation(GLuint program, const GLchar* name)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002380{
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002381 TRACE("(GLuint program = %d, const GLchar* name = 0x%0.8p)", program, name);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002382
2383 try
2384 {
2385 gl::Context *context = gl::getContext();
2386
2387 if (strstr(name, "gl_") == name)
2388 {
2389 return -1;
2390 }
2391
2392 if (context)
2393 {
2394 gl::Program *programObject = context->getProgram(program);
2395
2396 if (!programObject)
2397 {
2398 return error(GL_INVALID_VALUE, -1);
2399 }
2400
2401 if (!programObject->isLinked())
2402 {
2403 return error(GL_INVALID_OPERATION, -1);
2404 }
2405
2406 return programObject->getUniformLocation(name);
2407 }
2408 }
2409 catch(std::bad_alloc&)
2410 {
2411 return error(GL_OUT_OF_MEMORY, -1);
2412 }
2413
2414 return -1;
2415}
2416
2417void __stdcall glGetVertexAttribfv(GLuint index, GLenum pname, GLfloat* params)
2418{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002419 TRACE("(GLuint index = %d, GLenum pname = 0x%X, GLfloat* params = 0x%0.8p)", index, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002420
2421 try
2422 {
2423 if (index >= gl::MAX_VERTEX_ATTRIBS)
2424 {
2425 return error(GL_INVALID_VALUE);
2426 }
2427
2428 UNIMPLEMENTED(); // FIXME
2429 }
2430 catch(std::bad_alloc&)
2431 {
2432 return error(GL_OUT_OF_MEMORY);
2433 }
2434}
2435
2436void __stdcall glGetVertexAttribiv(GLuint index, GLenum pname, GLint* params)
2437{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002438 TRACE("(GLuint index = %d, GLenum pname = 0x%X, GLint* params = 0x%0.8p)", index, pname, params);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002439
2440 try
2441 {
2442 if (index >= gl::MAX_VERTEX_ATTRIBS)
2443 {
2444 return error(GL_INVALID_VALUE);
2445 }
2446
2447 UNIMPLEMENTED(); // FIXME
2448 }
2449 catch(std::bad_alloc&)
2450 {
2451 return error(GL_OUT_OF_MEMORY);
2452 }
2453}
2454
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002455void __stdcall glGetVertexAttribPointerv(GLuint index, GLenum pname, GLvoid** pointer)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002456{
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002457 TRACE("(GLuint index = %d, GLenum pname = 0x%X, GLvoid** pointer = 0x%0.8p)", index, pname, pointer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002458
2459 try
2460 {
2461 if (index >= gl::MAX_VERTEX_ATTRIBS)
2462 {
2463 return error(GL_INVALID_VALUE);
2464 }
2465
2466 UNIMPLEMENTED(); // FIXME
2467 }
2468 catch(std::bad_alloc&)
2469 {
2470 return error(GL_OUT_OF_MEMORY);
2471 }
2472}
2473
2474void __stdcall glHint(GLenum target, GLenum mode)
2475{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002476 TRACE("(GLenum target = 0x%X, GLenum mode = 0x%X)", target, mode);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002477
2478 try
2479 {
daniel@transgaming.com5949aa12010-03-21 04:31:15 +00002480 switch (target)
2481 {
2482 case GL_GENERATE_MIPMAP_HINT:
2483 switch (mode)
2484 {
2485 case GL_FASTEST:
2486 case GL_NICEST:
2487 case GL_DONT_CARE:
2488 break;
2489 default:
2490 return error(GL_INVALID_ENUM);
2491 }
2492 break;
2493 default:
2494 return error(GL_INVALID_ENUM);
2495 }
2496
2497 gl::Context *context = gl::getContext();
2498 if (context)
2499 {
2500 if (target == GL_GENERATE_MIPMAP_HINT)
2501 context->generateMipmapHint = mode;
2502 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002503 }
2504 catch(std::bad_alloc&)
2505 {
2506 return error(GL_OUT_OF_MEMORY);
2507 }
2508}
2509
2510GLboolean __stdcall glIsBuffer(GLuint buffer)
2511{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002512 TRACE("(GLuint buffer = %d)", buffer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002513
2514 try
2515 {
2516 gl::Context *context = gl::getContext();
2517
2518 if (context && buffer)
2519 {
2520 gl::Buffer *bufferObject = context->getBuffer(buffer);
2521
2522 if (bufferObject)
2523 {
2524 return GL_TRUE;
2525 }
2526 }
2527 }
2528 catch(std::bad_alloc&)
2529 {
2530 return error(GL_OUT_OF_MEMORY, GL_FALSE);
2531 }
2532
2533 return GL_FALSE;
2534}
2535
2536GLboolean __stdcall glIsEnabled(GLenum cap)
2537{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002538 TRACE("(GLenum cap = 0x%X)", cap);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002539
2540 try
2541 {
2542 gl::Context *context = gl::getContext();
2543
2544 if (context)
2545 {
2546 switch (cap)
2547 {
2548 case GL_CULL_FACE: return context->cullFace;
2549 case GL_POLYGON_OFFSET_FILL: return context->polygonOffsetFill;
2550 case GL_SAMPLE_ALPHA_TO_COVERAGE: return context->sampleAlphaToCoverage;
2551 case GL_SAMPLE_COVERAGE: return context->sampleCoverage;
2552 case GL_SCISSOR_TEST: return context->scissorTest;
2553 case GL_STENCIL_TEST: return context->stencilTest;
2554 case GL_DEPTH_TEST: return context->depthTest;
2555 case GL_BLEND: return context->blend;
2556 case GL_DITHER: return context->dither;
2557 default:
2558 return error(GL_INVALID_ENUM, false);
2559 }
2560 }
2561 }
2562 catch(std::bad_alloc&)
2563 {
2564 return error(GL_OUT_OF_MEMORY, false);
2565 }
2566
2567 return false;
2568}
2569
2570GLboolean __stdcall glIsFramebuffer(GLuint framebuffer)
2571{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002572 TRACE("(GLuint framebuffer = %d)", framebuffer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002573
2574 try
2575 {
2576 gl::Context *context = gl::getContext();
2577
2578 if (context && framebuffer)
2579 {
2580 gl::Framebuffer *framebufferObject = context->getFramebuffer(framebuffer);
2581
2582 if (framebufferObject)
2583 {
2584 return GL_TRUE;
2585 }
2586 }
2587 }
2588 catch(std::bad_alloc&)
2589 {
2590 return error(GL_OUT_OF_MEMORY, GL_FALSE);
2591 }
2592
2593 return GL_FALSE;
2594}
2595
2596GLboolean __stdcall glIsProgram(GLuint program)
2597{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002598 TRACE("(GLuint program = %d)", program);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002599
2600 try
2601 {
2602 gl::Context *context = gl::getContext();
2603
2604 if (context && program)
2605 {
2606 gl::Program *programObject = context->getProgram(program);
2607
2608 if (programObject)
2609 {
2610 return GL_TRUE;
2611 }
2612 }
2613 }
2614 catch(std::bad_alloc&)
2615 {
2616 return error(GL_OUT_OF_MEMORY, GL_FALSE);
2617 }
2618
2619 return GL_FALSE;
2620}
2621
2622GLboolean __stdcall glIsRenderbuffer(GLuint renderbuffer)
2623{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002624 TRACE("(GLuint renderbuffer = %d)", renderbuffer);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002625
2626 try
2627 {
2628 gl::Context *context = gl::getContext();
2629
2630 if (context && renderbuffer)
2631 {
2632 gl::Renderbuffer *renderbufferObject = context->getRenderbuffer(renderbuffer);
2633
2634 if (renderbufferObject)
2635 {
2636 return GL_TRUE;
2637 }
2638 }
2639 }
2640 catch(std::bad_alloc&)
2641 {
2642 return error(GL_OUT_OF_MEMORY, GL_FALSE);
2643 }
2644
2645 return GL_FALSE;
2646}
2647
2648GLboolean __stdcall glIsShader(GLuint shader)
2649{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002650 TRACE("(GLuint shader = %d)", shader);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002651
2652 try
2653 {
2654 gl::Context *context = gl::getContext();
2655
2656 if (context && shader)
2657 {
2658 gl::Shader *shaderObject = context->getShader(shader);
2659
2660 if (shaderObject)
2661 {
2662 return GL_TRUE;
2663 }
2664 }
2665 }
2666 catch(std::bad_alloc&)
2667 {
2668 return error(GL_OUT_OF_MEMORY, GL_FALSE);
2669 }
2670
2671 return GL_FALSE;
2672}
2673
2674GLboolean __stdcall glIsTexture(GLuint texture)
2675{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002676 TRACE("(GLuint texture = %d)", texture);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002677
2678 try
2679 {
2680 gl::Context *context = gl::getContext();
2681
2682 if (context && texture)
2683 {
2684 gl::Texture *textureObject = context->getTexture(texture);
2685
2686 if (textureObject)
2687 {
2688 return GL_TRUE;
2689 }
2690 }
2691 }
2692 catch(std::bad_alloc&)
2693 {
2694 return error(GL_OUT_OF_MEMORY, GL_FALSE);
2695 }
2696
2697 return GL_FALSE;
2698}
2699
2700void __stdcall glLineWidth(GLfloat width)
2701{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002702 TRACE("(GLfloat width = %f)", width);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002703
2704 try
2705 {
2706 if (width <= 0.0f)
2707 {
2708 return error(GL_INVALID_VALUE);
2709 }
2710
daniel@transgaming.com32e58cd2010-03-24 09:44:10 +00002711 gl::Context *context = gl::getContext();
2712
2713 if (context)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002714 {
daniel@transgaming.com32e58cd2010-03-24 09:44:10 +00002715 context->lineWidth = width;
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002716 }
2717 }
2718 catch(std::bad_alloc&)
2719 {
2720 return error(GL_OUT_OF_MEMORY);
2721 }
2722}
2723
2724void __stdcall glLinkProgram(GLuint program)
2725{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002726 TRACE("(GLuint program = %d)", program);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002727
2728 try
2729 {
2730 gl::Context *context = gl::getContext();
2731
2732 if (context)
2733 {
2734 gl::Program *programObject = context->getProgram(program);
2735
2736 if (!programObject)
2737 {
2738 return error(GL_INVALID_VALUE);
2739 }
2740
2741 programObject->link();
2742 }
2743 }
2744 catch(std::bad_alloc&)
2745 {
2746 return error(GL_OUT_OF_MEMORY);
2747 }
2748}
2749
2750void __stdcall glPixelStorei(GLenum pname, GLint param)
2751{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002752 TRACE("(GLenum pname = 0x%X, GLint param = %d)", pname, param);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002753
2754 try
2755 {
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00002756 gl::Context *context = gl::getContext();
2757
2758 if (context)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002759 {
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00002760 switch (pname)
2761 {
2762 case GL_UNPACK_ALIGNMENT:
2763 if (param != 1 && param != 2 && param != 4 && param != 8)
2764 {
2765 return error(GL_INVALID_VALUE);
2766 }
2767
2768 context->unpackAlignment = param;
2769 break;
2770
2771 case GL_PACK_ALIGNMENT:
2772 if (param != 1 && param != 2 && param != 4 && param != 8)
2773 {
2774 return error(GL_INVALID_VALUE);
2775 }
2776
2777 context->packAlignment = param;
2778 break;
2779
2780 default:
2781 return error(GL_INVALID_ENUM);
2782 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002783 }
2784 }
2785 catch(std::bad_alloc&)
2786 {
2787 return error(GL_OUT_OF_MEMORY);
2788 }
2789}
2790
2791void __stdcall glPolygonOffset(GLfloat factor, GLfloat units)
2792{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002793 TRACE("(GLfloat factor = %f, GLfloat units = %f)", factor, units);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002794
2795 try
2796 {
2797 if (factor != 0.0f || units != 0.0f)
2798 {
2799 UNIMPLEMENTED(); // FIXME
2800 }
2801 }
2802 catch(std::bad_alloc&)
2803 {
2804 return error(GL_OUT_OF_MEMORY);
2805 }
2806}
2807
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002808void __stdcall glReadPixels(GLint x, GLint y, GLsizei width, GLsizei height, GLenum format, GLenum type, GLvoid* pixels)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002809{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002810 TRACE("(GLint x = %d, GLint y = %d, GLsizei width = %d, GLsizei height = %d, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002811 "GLenum format = 0x%X, GLenum type = 0x%X, GLvoid* pixels = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002812 x, y, width, height, format, type, pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002813
2814 try
2815 {
2816 if (width < 0 || height < 0)
2817 {
2818 return error(GL_INVALID_VALUE);
2819 }
2820
2821 switch (format)
2822 {
2823 case GL_RGBA:
2824 switch (type)
2825 {
2826 case GL_UNSIGNED_BYTE:
2827 break;
2828 default:
2829 return error(GL_INVALID_OPERATION);
2830 }
2831 break;
2832 case gl::IMPLEMENTATION_COLOR_READ_FORMAT:
2833 switch (type)
2834 {
2835 case gl::IMPLEMENTATION_COLOR_READ_TYPE:
2836 break;
2837 default:
2838 return error(GL_INVALID_OPERATION);
2839 }
2840 break;
2841 default:
2842 return error(GL_INVALID_OPERATION);
2843 }
2844
2845 gl::Context *context = gl::getContext();
2846
2847 if (context)
2848 {
2849 context->readPixels(x, y, width, height, format, type, pixels);
2850 }
2851 }
2852 catch(std::bad_alloc&)
2853 {
2854 return error(GL_OUT_OF_MEMORY);
2855 }
2856}
2857
2858void __stdcall glReleaseShaderCompiler(void)
2859{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002860 TRACE("()");
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002861
2862 try
2863 {
2864 gl::Shader::releaseCompiler();
2865 }
2866 catch(std::bad_alloc&)
2867 {
2868 return error(GL_OUT_OF_MEMORY);
2869 }
2870}
2871
2872void __stdcall glRenderbufferStorage(GLenum target, GLenum internalformat, GLsizei width, GLsizei height)
2873{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002874 TRACE("(GLenum target = 0x%X, GLenum internalformat = 0x%X, GLsizei width = %d, GLsizei height = %d)",
2875 target, internalformat, width, height);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002876
2877 try
2878 {
2879 switch (target)
2880 {
2881 case GL_RENDERBUFFER:
2882 break;
2883 default:
2884 return error(GL_INVALID_ENUM);
2885 }
2886
2887 switch (internalformat)
2888 {
2889 case GL_DEPTH_COMPONENT16:
2890 case GL_RGBA4:
2891 case GL_RGB5_A1:
2892 case GL_RGB565:
2893 case GL_STENCIL_INDEX8:
2894 break;
2895 default:
2896 return error(GL_INVALID_ENUM);
2897 }
2898
2899 if (width < 0 || height < 0 || width > gl::MAX_RENDERBUFFER_SIZE || height > gl::MAX_RENDERBUFFER_SIZE)
2900 {
2901 return error(GL_INVALID_VALUE);
2902 }
2903
2904 gl::Context *context = gl::getContext();
2905
2906 if (context)
2907 {
2908 if (context->framebuffer == 0 || context->renderbuffer == 0)
2909 {
2910 return error(GL_INVALID_OPERATION);
2911 }
2912
2913 switch (internalformat)
2914 {
2915 case GL_DEPTH_COMPONENT16:
2916 context->setRenderbuffer(new gl::Depthbuffer(width, height));
2917 break;
2918 case GL_RGBA4:
2919 case GL_RGB5_A1:
2920 case GL_RGB565:
2921 UNIMPLEMENTED(); // FIXME
daniel@transgaming.com4a9d65c2010-03-08 21:30:56 +00002922 // context->setRenderbuffer(new Colorbuffer(renderTarget));
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002923 break;
2924 case GL_STENCIL_INDEX8:
daniel@transgaming.com4a9d65c2010-03-08 21:30:56 +00002925 context->setRenderbuffer(new gl::Stencilbuffer(width, height));
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002926 break;
2927 default:
2928 return error(GL_INVALID_ENUM);
2929 }
2930 }
2931 }
2932 catch(std::bad_alloc&)
2933 {
2934 return error(GL_OUT_OF_MEMORY);
2935 }
2936}
2937
2938void __stdcall glSampleCoverage(GLclampf value, GLboolean invert)
2939{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002940 TRACE("(GLclampf value = %f, GLboolean invert = %d)", value, invert);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002941
2942 try
2943 {
2944 gl::Context* context = gl::getContext();
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00002945
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002946 if (context)
2947 {
2948 context->sampleCoverageValue = gl::clamp01(value);
2949 context->sampleCoverageInvert = invert;
2950 }
2951 }
2952 catch(std::bad_alloc&)
2953 {
2954 return error(GL_OUT_OF_MEMORY);
2955 }
2956}
2957
2958void __stdcall glScissor(GLint x, GLint y, GLsizei width, GLsizei height)
2959{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002960 TRACE("(GLint x = %d, GLint y = %d, GLsizei width = %d, GLsizei height = %d)", x, y, width, height);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002961
2962 try
2963 {
2964 if (width < 0 || height < 0)
2965 {
2966 return error(GL_INVALID_VALUE);
2967 }
2968
2969 gl::Context* context = gl::getContext();
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00002970
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002971 if (context)
2972 {
2973 context->scissorX = x;
2974 context->scissorY = y;
2975 context->scissorWidth = width;
2976 context->scissorHeight = height;
2977 }
2978 }
2979 catch(std::bad_alloc&)
2980 {
2981 return error(GL_OUT_OF_MEMORY);
2982 }
2983}
2984
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002985void __stdcall glShaderBinary(GLsizei n, const GLuint* shaders, GLenum binaryformat, const GLvoid* binary, GLsizei length)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002986{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002987 TRACE("(GLsizei n = %d, const GLuint* shaders = 0x%0.8p, GLenum binaryformat = 0x%X, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00002988 "const GLvoid* binary = 0x%0.8p, GLsizei length = %d)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00002989 n, shaders, binaryformat, binary, length);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00002990
2991 try
2992 {
2993 if (n < 0 || length < 0)
2994 {
2995 return error(GL_INVALID_VALUE);
2996 }
2997
2998 UNIMPLEMENTED(); // FIXME
2999 }
3000 catch(std::bad_alloc&)
3001 {
3002 return error(GL_OUT_OF_MEMORY);
3003 }
3004}
3005
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00003006void __stdcall glShaderSource(GLuint shader, GLsizei count, const GLchar** string, const GLint* length)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003007{
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00003008 TRACE("(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 +00003009 shader, count, string, length);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003010
3011 try
3012 {
daniel@transgaming.com57a0bab2010-04-03 20:56:10 +00003013 if (shader == 0 || count < 0)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003014 {
3015 return error(GL_INVALID_VALUE);
3016 }
3017
3018 gl::Context *context = gl::getContext();
3019
3020 if (context)
3021 {
3022 gl::Shader *shaderObject = context->getShader(shader);
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00003023
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003024 if (!shaderObject)
3025 {
daniel@transgaming.com41187f12010-04-01 13:39:29 +00003026 return error(GL_INVALID_OPERATION);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003027 }
3028
3029 shaderObject->setSource(count, string, length);
3030 }
3031 }
3032 catch(std::bad_alloc&)
3033 {
3034 return error(GL_OUT_OF_MEMORY);
3035 }
3036}
3037
3038void __stdcall glStencilFunc(GLenum func, GLint ref, GLuint mask)
3039{
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00003040 glStencilFuncSeparate(GL_FRONT_AND_BACK, func, ref, mask);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003041}
3042
3043void __stdcall glStencilFuncSeparate(GLenum face, GLenum func, GLint ref, GLuint mask)
3044{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003045 TRACE("(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 +00003046
3047 try
3048 {
3049 switch (face)
3050 {
3051 case GL_FRONT:
3052 case GL_BACK:
3053 case GL_FRONT_AND_BACK:
3054 break;
3055 default:
3056 return error(GL_INVALID_ENUM);
3057 }
3058
3059 switch (func)
3060 {
3061 case GL_NEVER:
3062 case GL_ALWAYS:
3063 case GL_LESS:
3064 case GL_LEQUAL:
3065 case GL_EQUAL:
3066 case GL_GEQUAL:
3067 case GL_GREATER:
3068 case GL_NOTEQUAL:
3069 break;
3070 default:
3071 return error(GL_INVALID_ENUM);
3072 }
3073
3074 gl::Context *context = gl::getContext();
3075
3076 if (context)
3077 {
3078 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
3079 {
3080 context->stencilFunc = func;
3081 context->stencilRef = ref;
3082 context->stencilMask = mask;
3083 }
3084
3085 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
3086 {
3087 context->stencilBackFunc = func;
3088 context->stencilBackRef = ref;
3089 context->stencilBackMask = mask;
3090 }
3091 }
3092 }
3093 catch(std::bad_alloc&)
3094 {
3095 return error(GL_OUT_OF_MEMORY);
3096 }
3097}
3098
3099void __stdcall glStencilMask(GLuint mask)
3100{
3101 glStencilMaskSeparate(GL_FRONT_AND_BACK, mask);
3102}
3103
3104void __stdcall glStencilMaskSeparate(GLenum face, GLuint mask)
3105{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003106 TRACE("(GLenum face = 0x%X, GLuint mask = %d)", face, mask);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003107
3108 try
3109 {
3110 switch (face)
3111 {
3112 case GL_FRONT:
3113 case GL_BACK:
3114 case GL_FRONT_AND_BACK:
3115 break;
3116 default:
3117 return error(GL_INVALID_ENUM);
3118 }
3119
3120 gl::Context *context = gl::getContext();
3121
3122 if (context)
3123 {
3124 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
3125 {
3126 context->stencilWritemask = mask;
3127 }
3128
3129 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
3130 {
3131 context->stencilBackWritemask = mask;
3132 }
3133 }
3134 }
3135 catch(std::bad_alloc&)
3136 {
3137 return error(GL_OUT_OF_MEMORY);
3138 }
3139}
3140
3141void __stdcall glStencilOp(GLenum fail, GLenum zfail, GLenum zpass)
3142{
3143 glStencilOpSeparate(GL_FRONT_AND_BACK, fail, zfail, zpass);
3144}
3145
3146void __stdcall glStencilOpSeparate(GLenum face, GLenum fail, GLenum zfail, GLenum zpass)
3147{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003148 TRACE("(GLenum face = 0x%X, GLenum fail = 0x%X, GLenum zfail = 0x%X, GLenum zpas = 0x%Xs)",
3149 face, fail, zfail, zpass);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003150
3151 try
3152 {
3153 switch (face)
3154 {
3155 case GL_FRONT:
3156 case GL_BACK:
3157 case GL_FRONT_AND_BACK:
3158 break;
3159 default:
3160 return error(GL_INVALID_ENUM);
3161 }
3162
3163 switch (fail)
3164 {
3165 case GL_ZERO:
3166 case GL_KEEP:
3167 case GL_REPLACE:
3168 case GL_INCR:
3169 case GL_DECR:
3170 case GL_INVERT:
3171 case GL_INCR_WRAP:
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00003172 case GL_DECR_WRAP:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003173 break;
3174 default:
3175 return error(GL_INVALID_ENUM);
3176 }
3177
3178 switch (zfail)
3179 {
3180 case GL_ZERO:
3181 case GL_KEEP:
3182 case GL_REPLACE:
3183 case GL_INCR:
3184 case GL_DECR:
3185 case GL_INVERT:
3186 case GL_INCR_WRAP:
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00003187 case GL_DECR_WRAP:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003188 break;
3189 default:
3190 return error(GL_INVALID_ENUM);
3191 }
3192
3193 switch (zpass)
3194 {
3195 case GL_ZERO:
3196 case GL_KEEP:
3197 case GL_REPLACE:
3198 case GL_INCR:
3199 case GL_DECR:
3200 case GL_INVERT:
3201 case GL_INCR_WRAP:
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00003202 case GL_DECR_WRAP:
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003203 break;
3204 default:
3205 return error(GL_INVALID_ENUM);
3206 }
3207
3208 gl::Context *context = gl::getContext();
3209
3210 if (context)
3211 {
3212 if (face == GL_FRONT || face == GL_FRONT_AND_BACK)
3213 {
3214 context->stencilFail = fail;
3215 context->stencilPassDepthFail = zfail;
3216 context->stencilPassDepthPass = zpass;
3217 }
3218
3219 if (face == GL_BACK || face == GL_FRONT_AND_BACK)
3220 {
3221 context->stencilBackFail = fail;
3222 context->stencilBackPassDepthFail = zfail;
3223 context->stencilBackPassDepthPass = zpass;
3224 }
3225 }
3226 }
3227 catch(std::bad_alloc&)
3228 {
3229 return error(GL_OUT_OF_MEMORY);
3230 }
3231}
3232
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00003233void __stdcall glTexImage2D(GLenum target, GLint level, GLint internalformat, GLsizei width, GLsizei height,
3234 GLint border, GLenum format, GLenum type, const GLvoid* pixels)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003235{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003236 TRACE("(GLenum target = 0x%X, GLint level = %d, GLint internalformat = %d, GLsizei width = %d, GLsizei height = %d, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00003237 "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 +00003238 target, level, internalformat, width, height, border, format, type, pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003239
3240 try
3241 {
3242 if (level < 0 || width < 0 || height < 0)
3243 {
3244 return error(GL_INVALID_VALUE);
3245 }
3246
3247 if (level > 0 && (!gl::isPow2(width) || !gl::isPow2(height)))
3248 {
3249 return error(GL_INVALID_VALUE);
3250 }
daniel@transgaming.comfab5a1a2010-03-11 19:22:30 +00003251
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003252 switch (target)
3253 {
3254 case GL_TEXTURE_2D:
3255 if (width > (gl::MAX_TEXTURE_SIZE >> level) || height > (gl::MAX_TEXTURE_SIZE >> level))
3256 {
3257 return error(GL_INVALID_VALUE);
3258 }
3259 break;
3260 case GL_TEXTURE_CUBE_MAP_POSITIVE_X:
3261 case GL_TEXTURE_CUBE_MAP_NEGATIVE_X:
3262 case GL_TEXTURE_CUBE_MAP_POSITIVE_Y:
3263 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y:
3264 case GL_TEXTURE_CUBE_MAP_POSITIVE_Z:
3265 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z:
3266 if (!gl::isPow2(width) || !gl::isPow2(height))
3267 {
3268 return error(GL_INVALID_VALUE);
3269 }
3270
3271 if (width > (gl::MAX_CUBE_MAP_TEXTURE_SIZE >> level) || height > (gl::MAX_CUBE_MAP_TEXTURE_SIZE >> level))
3272 {
3273 return error(GL_INVALID_VALUE);
3274 }
3275 break;
3276 default:
3277 return error(GL_INVALID_ENUM);
3278 }
3279
3280 if (internalformat != format)
3281 {
3282 return error(GL_INVALID_OPERATION);
3283 }
3284
3285 switch (internalformat)
3286 {
3287 case GL_ALPHA:
3288 case GL_LUMINANCE:
3289 case GL_LUMINANCE_ALPHA:
3290 switch (type)
3291 {
3292 case GL_UNSIGNED_BYTE:
3293 break;
3294 default:
3295 return error(GL_INVALID_ENUM);
3296 }
3297 break;
3298 case GL_RGB:
3299 switch (type)
3300 {
3301 case GL_UNSIGNED_BYTE:
3302 case GL_UNSIGNED_SHORT_5_6_5:
3303 break;
3304 default:
3305 return error(GL_INVALID_ENUM);
3306 }
3307 break;
3308 case GL_RGBA:
3309 switch (type)
3310 {
3311 case GL_UNSIGNED_BYTE:
3312 case GL_UNSIGNED_SHORT_4_4_4_4:
3313 case GL_UNSIGNED_SHORT_5_5_5_1:
3314 break;
3315 default:
3316 return error(GL_INVALID_ENUM);
3317 }
3318 break;
3319 default:
3320 return error(GL_INVALID_VALUE);
3321 }
3322
3323 if (border != 0)
3324 {
3325 return error(GL_INVALID_VALUE);
3326 }
3327
3328 gl::Context *context = gl::getContext();
3329
3330 if (context)
3331 {
3332 if (target == GL_TEXTURE_2D)
3333 {
3334 gl::Texture2D *texture = context->getTexture2D();
3335
3336 if (!texture)
3337 {
3338 return error(GL_INVALID_OPERATION);
3339 }
3340
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00003341 texture->setImage(level, internalformat, width, height, format, type, context->unpackAlignment, pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003342 }
3343 else
3344 {
3345 gl::TextureCubeMap *texture = context->getTextureCubeMap();
3346
3347 if (!texture)
3348 {
3349 return error(GL_INVALID_OPERATION);
3350 }
3351
3352 switch (target)
3353 {
3354 case GL_TEXTURE_CUBE_MAP_POSITIVE_X:
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00003355 texture->setImagePosX(level, internalformat, width, height, format, type, context->unpackAlignment, pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003356 break;
3357 case GL_TEXTURE_CUBE_MAP_NEGATIVE_X:
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00003358 texture->setImageNegX(level, internalformat, width, height, format, type, context->unpackAlignment, pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003359 break;
3360 case GL_TEXTURE_CUBE_MAP_POSITIVE_Y:
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00003361 texture->setImagePosY(level, internalformat, width, height, format, type, context->unpackAlignment, pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003362 break;
3363 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y:
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00003364 texture->setImageNegY(level, internalformat, width, height, format, type, context->unpackAlignment, pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003365 break;
3366 case GL_TEXTURE_CUBE_MAP_POSITIVE_Z:
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00003367 texture->setImagePosZ(level, internalformat, width, height, format, type, context->unpackAlignment, pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003368 break;
3369 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z:
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00003370 texture->setImageNegZ(level, internalformat, width, height, format, type, context->unpackAlignment, pixels);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003371 break;
3372 default: UNREACHABLE();
3373 }
3374 }
3375 }
3376 }
3377 catch(std::bad_alloc&)
3378 {
3379 return error(GL_OUT_OF_MEMORY);
3380 }
3381}
3382
3383void __stdcall glTexParameterf(GLenum target, GLenum pname, GLfloat param)
3384{
3385 glTexParameteri(target, pname, (GLint)param);
3386}
3387
3388void __stdcall glTexParameterfv(GLenum target, GLenum pname, const GLfloat* params)
3389{
3390 glTexParameteri(target, pname, (GLint)*params);
3391}
3392
3393void __stdcall glTexParameteri(GLenum target, GLenum pname, GLint param)
3394{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003395 TRACE("(GLenum target = 0x%X, GLenum pname = 0x%X, GLfloat param = %f)", target, pname, param);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003396
3397 try
3398 {
3399 gl::Context *context = gl::getContext();
3400
3401 if (context)
3402 {
3403 gl::Texture *texture;
3404
3405 switch (target)
3406 {
3407 case GL_TEXTURE_2D:
3408 texture = context->getTexture2D();
3409 break;
3410 case GL_TEXTURE_CUBE_MAP:
3411 texture = context->getTextureCubeMap();
3412 break;
3413 default:
3414 return error(GL_INVALID_ENUM);
3415 }
3416
3417 switch (pname)
3418 {
3419 case GL_TEXTURE_WRAP_S:
3420 if (!texture->setWrapS((GLenum)param))
3421 {
3422 return error(GL_INVALID_ENUM);
3423 }
3424 break;
3425 case GL_TEXTURE_WRAP_T:
3426 if (!texture->setWrapT((GLenum)param))
3427 {
3428 return error(GL_INVALID_ENUM);
3429 }
3430 break;
3431 case GL_TEXTURE_MIN_FILTER:
3432 if (!texture->setMinFilter((GLenum)param))
3433 {
3434 return error(GL_INVALID_ENUM);
3435 }
3436 break;
3437 case GL_TEXTURE_MAG_FILTER:
3438 if (!texture->setMagFilter((GLenum)param))
3439 {
3440 return error(GL_INVALID_ENUM);
3441 }
3442 break;
3443 default:
3444 return error(GL_INVALID_ENUM);
3445 }
3446 }
3447 }
3448 catch(std::bad_alloc&)
3449 {
3450 return error(GL_OUT_OF_MEMORY);
3451 }
3452}
3453
3454void __stdcall glTexParameteriv(GLenum target, GLenum pname, const GLint* params)
3455{
3456 glTexParameteri(target, pname, *params);
3457}
3458
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00003459void __stdcall glTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
3460 GLenum format, GLenum type, const GLvoid* pixels)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003461{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003462 TRACE("(GLenum target = 0x%X, GLint level = %d, GLint xoffset = %d, GLint yoffset = %d, "
3463 "GLsizei width = %d, GLsizei height = %d, GLenum format = 0x%X, GLenum type = 0x%X, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00003464 "const GLvoid* pixels = 0x%0.8p)",
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003465 target, level, xoffset, yoffset, width, height, format, type, pixels);
3466
3467 try
3468 {
daniel@transgaming.com00c75962010-03-11 20:36:15 +00003469 if (target != GL_TEXTURE_2D && !es2dx::IsCubemapTextureTarget(target))
3470 {
3471 return error(GL_INVALID_ENUM);
3472 }
3473
3474 if (level < 0 || level > gl::MAX_TEXTURE_LEVELS || xoffset < 0 || yoffset < 0 || width < 0 || height < 0)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003475 {
3476 return error(GL_INVALID_VALUE);
3477 }
3478
daniel@transgaming.com00c75962010-03-11 20:36:15 +00003479 if (std::numeric_limits<GLsizei>::max() - xoffset < width || std::numeric_limits<GLsizei>::max() - yoffset < height)
3480 {
3481 return error(GL_INVALID_VALUE);
3482 }
3483
3484 if (!es2dx::CheckTextureFormatType(format, type))
3485 {
3486 return error(GL_INVALID_ENUM);
3487 }
3488
3489 if (width == 0 || height == 0 || pixels == NULL)
3490 {
3491 return;
3492 }
3493
3494 gl::Context *context = gl::getContext();
3495
3496 if (context)
3497 {
3498 if (target == GL_TEXTURE_2D)
3499 {
3500 gl::Texture2D *texture = context->getTexture2D();
3501
3502 if (!texture)
3503 {
3504 return error(GL_INVALID_OPERATION);
3505 }
3506
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00003507 texture->subImage(level, xoffset, yoffset, width, height, format, type, context->unpackAlignment, pixels);
daniel@transgaming.com00c75962010-03-11 20:36:15 +00003508 }
3509 else if (es2dx::IsCubemapTextureTarget(target))
3510 {
3511 gl::TextureCubeMap *texture = context->getTextureCubeMap();
3512
3513 if (!texture)
3514 {
3515 return error(GL_INVALID_OPERATION);
3516 }
3517
daniel@transgaming.com3489e3a2010-03-21 04:31:11 +00003518 texture->subImage(target, level, xoffset, yoffset, width, height, format, type, context->unpackAlignment, pixels);
daniel@transgaming.com00c75962010-03-11 20:36:15 +00003519 }
3520 else
3521 {
3522 UNREACHABLE();
3523 }
3524 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003525 }
3526 catch(std::bad_alloc&)
3527 {
3528 return error(GL_OUT_OF_MEMORY);
3529 }
3530}
3531
3532void __stdcall glUniform1f(GLint location, GLfloat x)
3533{
3534 glUniform1fv(location, 1, &x);
3535}
3536
3537void __stdcall glUniform1fv(GLint location, GLsizei count, const GLfloat* v)
3538{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003539 TRACE("(GLint location = %d, GLsizei count = %d, const GLfloat* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003540
3541 try
3542 {
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003543 if (count < 0)
3544 {
3545 return error(GL_INVALID_VALUE);
3546 }
3547
daniel@transgaming.com9a95e2b2010-04-13 03:26:03 +00003548 if (location == -1)
3549 {
3550 return;
3551 }
3552
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003553 gl::Context *context = gl::getContext();
3554
3555 if (context)
3556 {
3557 gl::Program *program = context->getCurrentProgram();
3558
3559 if (!program)
3560 {
3561 return error(GL_INVALID_OPERATION);
3562 }
3563
3564 if (!program->setUniform1fv(location, count, v))
3565 {
3566 return error(GL_INVALID_OPERATION);
3567 }
3568 }
3569 }
3570 catch(std::bad_alloc&)
3571 {
3572 return error(GL_OUT_OF_MEMORY);
3573 }
3574}
3575
3576void __stdcall glUniform1i(GLint location, GLint x)
3577{
3578 glUniform1iv(location, 1, &x);
3579}
3580
3581void __stdcall glUniform1iv(GLint location, GLsizei count, const GLint* v)
3582{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003583 TRACE("(GLint location = %d, GLsizei count = %d, const GLint* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003584
3585 try
3586 {
3587 if (count < 0)
3588 {
3589 return error(GL_INVALID_VALUE);
3590 }
3591
daniel@transgaming.com9a95e2b2010-04-13 03:26:03 +00003592 if (location == -1)
3593 {
3594 return;
3595 }
3596
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003597 gl::Context *context = gl::getContext();
3598
3599 if (context)
3600 {
3601 gl::Program *program = context->getCurrentProgram();
3602
3603 if (!program)
3604 {
3605 return error(GL_INVALID_OPERATION);
3606 }
3607
3608 if (!program->setUniform1iv(location, count, v))
3609 {
3610 return error(GL_INVALID_OPERATION);
3611 }
3612 }
3613 }
3614 catch(std::bad_alloc&)
3615 {
3616 return error(GL_OUT_OF_MEMORY);
3617 }
3618}
3619
3620void __stdcall glUniform2f(GLint location, GLfloat x, GLfloat y)
3621{
3622 GLfloat xy[2] = {x, y};
3623
3624 glUniform2fv(location, 1, (GLfloat*)&xy);
3625}
3626
3627void __stdcall glUniform2fv(GLint location, GLsizei count, const GLfloat* v)
3628{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003629 TRACE("(GLint location = %d, GLsizei count = %d, const GLfloat* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003630
3631 try
3632 {
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003633 if (count < 0)
3634 {
3635 return error(GL_INVALID_VALUE);
3636 }
daniel@transgaming.com9a95e2b2010-04-13 03:26:03 +00003637
3638 if (location == -1)
3639 {
3640 return;
3641 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003642
3643 gl::Context *context = gl::getContext();
3644
3645 if (context)
3646 {
3647 gl::Program *program = context->getCurrentProgram();
3648
3649 if (!program)
3650 {
3651 return error(GL_INVALID_OPERATION);
3652 }
3653
3654 if (!program->setUniform2fv(location, count, v))
3655 {
3656 return error(GL_INVALID_OPERATION);
3657 }
3658 }
3659 }
3660 catch(std::bad_alloc&)
3661 {
3662 return error(GL_OUT_OF_MEMORY);
3663 }
3664}
3665
3666void __stdcall glUniform2i(GLint location, GLint x, GLint y)
3667{
3668 GLint xy[4] = {x, y};
3669
3670 glUniform2iv(location, 1, (GLint*)&xy);
3671}
3672
3673void __stdcall glUniform2iv(GLint location, GLsizei count, const GLint* v)
3674{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003675 TRACE("(GLint location = %d, GLsizei count = %d, const GLint* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003676
3677 try
3678 {
3679 if (count < 0)
3680 {
3681 return error(GL_INVALID_VALUE);
3682 }
3683
daniel@transgaming.com9a95e2b2010-04-13 03:26:03 +00003684 if (location == -1)
3685 {
3686 return;
3687 }
3688
3689 gl::Context *context = gl::getContext();
3690
3691 if (context)
3692 {
3693 gl::Program *program = context->getCurrentProgram();
3694
3695 if (!program)
3696 {
3697 return error(GL_INVALID_OPERATION);
3698 }
3699
3700 if (!program->setUniform2iv(location, count, v))
3701 {
3702 return error(GL_INVALID_OPERATION);
3703 }
3704 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003705 }
3706 catch(std::bad_alloc&)
3707 {
3708 return error(GL_OUT_OF_MEMORY);
3709 }
3710}
3711
3712void __stdcall glUniform3f(GLint location, GLfloat x, GLfloat y, GLfloat z)
3713{
3714 GLfloat xyz[3] = {x, y, z};
3715
3716 glUniform3fv(location, 1, (GLfloat*)&xyz);
3717}
3718
3719void __stdcall glUniform3fv(GLint location, GLsizei count, const GLfloat* v)
3720{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003721 TRACE("(GLint location = %d, GLsizei count = %d, const GLfloat* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003722
3723 try
3724 {
3725 if (count < 0)
3726 {
3727 return error(GL_INVALID_VALUE);
3728 }
3729
3730 if (location == -1)
3731 {
3732 return;
3733 }
3734
3735 gl::Context *context = gl::getContext();
3736
3737 if (context)
3738 {
3739 gl::Program *program = context->getCurrentProgram();
3740
3741 if (!program)
3742 {
3743 return error(GL_INVALID_OPERATION);
3744 }
3745
3746 if (!program->setUniform3fv(location, count, v))
3747 {
3748 return error(GL_INVALID_OPERATION);
3749 }
3750 }
3751 }
3752 catch(std::bad_alloc&)
3753 {
3754 return error(GL_OUT_OF_MEMORY);
3755 }
3756}
3757
3758void __stdcall glUniform3i(GLint location, GLint x, GLint y, GLint z)
3759{
3760 GLint xyz[3] = {x, y, z};
3761
3762 glUniform3iv(location, 1, (GLint*)&xyz);
3763}
3764
3765void __stdcall glUniform3iv(GLint location, GLsizei count, const GLint* v)
3766{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003767 TRACE("(GLint location = %d, GLsizei count = %d, const GLint* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003768
3769 try
3770 {
3771 if (count < 0)
3772 {
3773 return error(GL_INVALID_VALUE);
3774 }
3775
daniel@transgaming.com9a95e2b2010-04-13 03:26:03 +00003776 if (location == -1)
3777 {
3778 return;
3779 }
3780
3781 gl::Context *context = gl::getContext();
3782
3783 if (context)
3784 {
3785 gl::Program *program = context->getCurrentProgram();
3786
3787 if (!program)
3788 {
3789 return error(GL_INVALID_OPERATION);
3790 }
3791
3792 if (!program->setUniform3iv(location, count, v))
3793 {
3794 return error(GL_INVALID_OPERATION);
3795 }
3796 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003797 }
3798 catch(std::bad_alloc&)
3799 {
3800 return error(GL_OUT_OF_MEMORY);
3801 }
3802}
3803
3804void __stdcall glUniform4f(GLint location, GLfloat x, GLfloat y, GLfloat z, GLfloat w)
3805{
3806 GLfloat xyzw[4] = {x, y, z, w};
3807
3808 glUniform4fv(location, 1, (GLfloat*)&xyzw);
3809}
3810
3811void __stdcall glUniform4fv(GLint location, GLsizei count, const GLfloat* v)
3812{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003813 TRACE("(GLint location = %d, GLsizei count = %d, const GLfloat* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003814
3815 try
3816 {
3817 if (count < 0)
3818 {
3819 return error(GL_INVALID_VALUE);
3820 }
3821
3822 if (location == -1)
3823 {
3824 return;
3825 }
3826
3827 gl::Context *context = gl::getContext();
3828
3829 if (context)
3830 {
3831 gl::Program *program = context->getCurrentProgram();
3832
3833 if (!program)
3834 {
3835 return error(GL_INVALID_OPERATION);
3836 }
3837
3838 if (!program->setUniform4fv(location, count, v))
3839 {
3840 return error(GL_INVALID_OPERATION);
3841 }
3842 }
3843 }
3844 catch(std::bad_alloc&)
3845 {
3846 return error(GL_OUT_OF_MEMORY);
3847 }
3848}
3849
3850void __stdcall glUniform4i(GLint location, GLint x, GLint y, GLint z, GLint w)
3851{
3852 GLint xyzw[4] = {x, y, z, w};
3853
3854 glUniform4iv(location, 1, (GLint*)&xyzw);
3855}
3856
3857void __stdcall glUniform4iv(GLint location, GLsizei count, const GLint* v)
3858{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003859 TRACE("(GLint location = %d, GLsizei count = %d, const GLint* v = 0x%0.8p)", location, count, v);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003860
3861 try
3862 {
3863 if (count < 0)
3864 {
3865 return error(GL_INVALID_VALUE);
3866 }
3867
daniel@transgaming.com9a95e2b2010-04-13 03:26:03 +00003868 if (location == -1)
3869 {
3870 return;
3871 }
3872
3873 gl::Context *context = gl::getContext();
3874
3875 if (context)
3876 {
3877 gl::Program *program = context->getCurrentProgram();
3878
3879 if (!program)
3880 {
3881 return error(GL_INVALID_OPERATION);
3882 }
3883
3884 if (!program->setUniform4iv(location, count, v))
3885 {
3886 return error(GL_INVALID_OPERATION);
3887 }
3888 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003889 }
3890 catch(std::bad_alloc&)
3891 {
3892 return error(GL_OUT_OF_MEMORY);
3893 }
3894}
3895
3896void __stdcall glUniformMatrix2fv(GLint location, GLsizei count, GLboolean transpose, const GLfloat* value)
3897{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003898 TRACE("(GLint location = %d, GLsizei count = %d, GLboolean transpose = %d, const GLfloat* value = 0x%0.8p)",
3899 location, count, transpose, value);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003900
3901 try
3902 {
3903 if (count < 0 || transpose != GL_FALSE)
3904 {
3905 return error(GL_INVALID_VALUE);
3906 }
3907
3908 if (location == -1)
3909 {
3910 return;
3911 }
3912
3913 gl::Context *context = gl::getContext();
3914
3915 if (context)
3916 {
3917 gl::Program *program = context->getCurrentProgram();
3918
3919 if (!program)
3920 {
3921 return error(GL_INVALID_OPERATION);
3922 }
3923
3924 if (!program->setUniformMatrix2fv(location, count, value))
3925 {
3926 return error(GL_INVALID_OPERATION);
3927 }
3928 }
3929 }
3930 catch(std::bad_alloc&)
3931 {
3932 return error(GL_OUT_OF_MEMORY);
3933 }
3934}
3935
3936void __stdcall glUniformMatrix3fv(GLint location, GLsizei count, GLboolean transpose, const GLfloat* value)
3937{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003938 TRACE("(GLint location = %d, GLsizei count = %d, GLboolean transpose = %d, const GLfloat* value = 0x%0.8p)",
3939 location, count, transpose, value);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003940
3941 try
3942 {
3943 if (count < 0 || transpose != GL_FALSE)
3944 {
3945 return error(GL_INVALID_VALUE);
3946 }
3947
3948 if (location == -1)
3949 {
3950 return;
3951 }
3952
3953 gl::Context *context = gl::getContext();
3954
3955 if (context)
3956 {
3957 gl::Program *program = context->getCurrentProgram();
3958
3959 if (!program)
3960 {
3961 return error(GL_INVALID_OPERATION);
3962 }
3963
3964 if (!program->setUniformMatrix3fv(location, count, value))
3965 {
3966 return error(GL_INVALID_OPERATION);
3967 }
3968 }
3969 }
3970 catch(std::bad_alloc&)
3971 {
3972 return error(GL_OUT_OF_MEMORY);
3973 }
3974}
3975
3976void __stdcall glUniformMatrix4fv(GLint location, GLsizei count, GLboolean transpose, const GLfloat* value)
3977{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00003978 TRACE("(GLint location = %d, GLsizei count = %d, GLboolean transpose = %d, const GLfloat* value = 0x%0.8p)",
3979 location, count, transpose, value);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003980
3981 try
3982 {
3983 if (count < 0 || transpose != GL_FALSE)
3984 {
3985 return error(GL_INVALID_VALUE);
3986 }
3987
3988 if (location == -1)
3989 {
3990 return;
3991 }
3992
3993 gl::Context *context = gl::getContext();
3994
3995 if (context)
3996 {
3997 gl::Program *program = context->getCurrentProgram();
3998
3999 if (!program)
4000 {
4001 return error(GL_INVALID_OPERATION);
4002 }
4003
4004 if (!program->setUniformMatrix4fv(location, count, value))
4005 {
4006 return error(GL_INVALID_OPERATION);
4007 }
4008 }
4009 }
4010 catch(std::bad_alloc&)
4011 {
4012 return error(GL_OUT_OF_MEMORY);
4013 }
4014}
4015
4016void __stdcall glUseProgram(GLuint program)
4017{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004018 TRACE("(GLuint program = %d)", program);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004019
4020 try
4021 {
4022 gl::Context *context = gl::getContext();
4023
4024 if (context)
4025 {
4026 gl::Program *programObject = context->getProgram(program);
4027
4028 if (programObject && !programObject->isLinked())
4029 {
4030 return error(GL_INVALID_OPERATION);
4031 }
4032
4033 context->useProgram(program);
4034 }
4035 }
4036 catch(std::bad_alloc&)
4037 {
4038 return error(GL_OUT_OF_MEMORY);
4039 }
4040}
4041
4042void __stdcall glValidateProgram(GLuint program)
4043{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004044 TRACE("(GLuint program = %d)", program);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004045
4046 try
4047 {
4048 UNIMPLEMENTED(); // FIXME
4049 }
4050 catch(std::bad_alloc&)
4051 {
4052 return error(GL_OUT_OF_MEMORY);
4053 }
4054}
4055
4056void __stdcall glVertexAttrib1f(GLuint index, GLfloat x)
4057{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004058 TRACE("(GLuint index = %d, GLfloat x = %f)", index, x);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004059
4060 try
4061 {
4062 if (index >= gl::MAX_VERTEX_ATTRIBS)
4063 {
4064 return error(GL_INVALID_VALUE);
4065 }
4066
4067 UNIMPLEMENTED(); // FIXME
4068 }
4069 catch(std::bad_alloc&)
4070 {
4071 return error(GL_OUT_OF_MEMORY);
4072 }
4073}
4074
4075void __stdcall glVertexAttrib1fv(GLuint index, const GLfloat* values)
4076{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004077 TRACE("(GLuint index = %d, const GLfloat* values = 0x%0.8p)", index, values);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004078
4079 try
4080 {
4081 if (index >= gl::MAX_VERTEX_ATTRIBS)
4082 {
4083 return error(GL_INVALID_VALUE);
4084 }
4085
4086 UNIMPLEMENTED(); // FIXME
4087 }
4088 catch(std::bad_alloc&)
4089 {
4090 return error(GL_OUT_OF_MEMORY);
4091 }
4092}
4093
4094void __stdcall glVertexAttrib2f(GLuint index, GLfloat x, GLfloat y)
4095{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004096 TRACE("(GLuint index = %d, GLfloat x = %f, GLfloat y = %f)", index, x, y);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004097
4098 try
4099 {
4100 if (index >= gl::MAX_VERTEX_ATTRIBS)
4101 {
4102 return error(GL_INVALID_VALUE);
4103 }
4104
4105 UNIMPLEMENTED(); // FIXME
4106 }
4107 catch(std::bad_alloc&)
4108 {
4109 return error(GL_OUT_OF_MEMORY);
4110 }
4111}
4112
4113void __stdcall glVertexAttrib2fv(GLuint index, const GLfloat* values)
4114{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004115 TRACE("(GLuint index = %d, const GLfloat* values = 0x%0.8p)", index, values);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004116
4117 try
4118 {
4119 if (index >= gl::MAX_VERTEX_ATTRIBS)
4120 {
4121 return error(GL_INVALID_VALUE);
4122 }
4123
4124 UNIMPLEMENTED(); // FIXME
4125 }
4126 catch(std::bad_alloc&)
4127 {
4128 return error(GL_OUT_OF_MEMORY);
4129 }
4130}
4131
4132void __stdcall glVertexAttrib3f(GLuint index, GLfloat x, GLfloat y, GLfloat z)
4133{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004134 TRACE("(GLuint index = %d, GLfloat x = %f, GLfloat y = %f, GLfloat z = %f)", index, x, y, z);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004135
4136 try
4137 {
4138 if (index >= gl::MAX_VERTEX_ATTRIBS)
4139 {
4140 return error(GL_INVALID_VALUE);
4141 }
4142
4143 UNIMPLEMENTED(); // FIXME
4144 }
4145 catch(std::bad_alloc&)
4146 {
4147 return error(GL_OUT_OF_MEMORY);
4148 }
4149}
4150
4151void __stdcall glVertexAttrib3fv(GLuint index, const GLfloat* values)
4152{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004153 TRACE("(GLuint index = %d, const GLfloat* values = 0x%0.8p)", index, values);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004154
4155 try
4156 {
4157 if (index >= gl::MAX_VERTEX_ATTRIBS)
4158 {
4159 return error(GL_INVALID_VALUE);
4160 }
4161
4162 UNIMPLEMENTED(); // FIXME
4163 }
4164 catch(std::bad_alloc&)
4165 {
4166 return error(GL_OUT_OF_MEMORY);
4167 }
4168}
4169
4170void __stdcall glVertexAttrib4f(GLuint index, GLfloat x, GLfloat y, GLfloat z, GLfloat w)
4171{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004172 TRACE("(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 +00004173
4174 try
4175 {
4176 if (index >= gl::MAX_VERTEX_ATTRIBS)
4177 {
4178 return error(GL_INVALID_VALUE);
4179 }
4180
4181 UNIMPLEMENTED(); // FIXME
4182 }
4183 catch(std::bad_alloc&)
4184 {
4185 return error(GL_OUT_OF_MEMORY);
4186 }
4187}
4188
4189void __stdcall glVertexAttrib4fv(GLuint index, const GLfloat* values)
4190{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004191 TRACE("(GLuint index = %d, const GLfloat* values = 0x%0.8p)", index, values);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004192
4193 try
4194 {
4195 if (index >= gl::MAX_VERTEX_ATTRIBS)
4196 {
4197 return error(GL_INVALID_VALUE);
4198 }
4199
4200 UNIMPLEMENTED(); // FIXME
4201 }
4202 catch(std::bad_alloc&)
4203 {
4204 return error(GL_OUT_OF_MEMORY);
4205 }
4206}
4207
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00004208void __stdcall glVertexAttribPointer(GLuint index, GLint size, GLenum type, GLboolean normalized, GLsizei stride, const GLvoid* ptr)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004209{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004210 TRACE("(GLuint index = %d, GLint size = %d, GLenum type = 0x%X, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00004211 "GLboolean normalized = %d, GLsizei stride = %d, const GLvoid* ptr = 0x%0.8p)",
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004212 index, size, type, normalized, stride, ptr);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004213
4214 try
4215 {
4216 if (index >= gl::MAX_VERTEX_ATTRIBS)
4217 {
4218 return error(GL_INVALID_VALUE);
4219 }
4220
4221 if (size < 1 || size > 4)
4222 {
4223 return error(GL_INVALID_VALUE);
4224 }
4225
4226 switch (type)
4227 {
4228 case GL_BYTE:
4229 case GL_UNSIGNED_BYTE:
4230 case GL_SHORT:
4231 case GL_UNSIGNED_SHORT:
4232 case GL_FIXED:
4233 case GL_FLOAT:
4234 break;
4235 default:
4236 return error(GL_INVALID_ENUM);
4237 }
4238
4239 if (stride < 0)
4240 {
4241 return error(GL_INVALID_VALUE);
4242 }
4243
4244 gl::Context *context = gl::getContext();
4245
4246 if (context)
4247 {
daniel@transgaming.com0f7aaf52010-03-11 19:41:38 +00004248 context->vertexAttribute[index].mBoundBuffer = context->arrayBuffer;
4249 context->vertexAttribute[index].mSize = size;
4250 context->vertexAttribute[index].mType = type;
daniel@transgaming.comb994e3b2010-03-26 04:08:50 +00004251 context->vertexAttribute[index].mNormalized = (normalized == GL_TRUE);
daniel@transgaming.com0f7aaf52010-03-11 19:41:38 +00004252 context->vertexAttribute[index].mStride = stride;
4253 context->vertexAttribute[index].mPointer = ptr;
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004254 }
4255 }
4256 catch(std::bad_alloc&)
4257 {
4258 return error(GL_OUT_OF_MEMORY);
4259 }
4260}
4261
4262void __stdcall glViewport(GLint x, GLint y, GLsizei width, GLsizei height)
4263{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004264 TRACE("(GLint x = %d, GLint y = %d, GLsizei width = %d, GLsizei height = %d)", x, y, width, height);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004265
4266 try
4267 {
4268 if (width < 0 || height < 0)
4269 {
4270 return error(GL_INVALID_VALUE);
4271 }
4272
4273 gl::Context *context = gl::getContext();
4274
4275 if (context)
4276 {
4277 context->viewportX = x;
4278 context->viewportY = y;
4279 context->viewportWidth = width;
4280 context->viewportHeight = height;
4281 }
4282 }
4283 catch(std::bad_alloc&)
4284 {
4285 return error(GL_OUT_OF_MEMORY);
4286 }
4287}
4288
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00004289void __stdcall glTexImage3DOES(GLenum target, GLint level, GLenum internalformat, GLsizei width, GLsizei height, GLsizei depth,
4290 GLint border, GLenum format, GLenum type, const GLvoid* pixels)
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004291{
daniel@transgaming.comb5b06162010-03-21 04:31:32 +00004292 TRACE("(GLenum target = 0x%X, GLint level = %d, GLenum internalformat = 0x%X, "
4293 "GLsizei width = %d, GLsizei height = %d, GLsizei depth = %d, GLint border = %d, "
daniel@transgaming.comfe4b8272010-04-08 03:51:20 +00004294 "GLenum format = 0x%X, GLenum type = 0x%x, const GLvoid* pixels = 0x%0.8p)",
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00004295 target, level, internalformat, width, height, depth, border, format, type, pixels);
4296
4297 try
4298 {
4299 UNIMPLEMENTED(); // FIXME
4300 }
4301 catch(std::bad_alloc&)
4302 {
4303 return error(GL_OUT_OF_MEMORY);
4304 }
4305}
4306}