/* * Copyright (C) 2010 - 2011 Samsung Electronics Co., Ltd. All rights reserved. * * Contact: * DongKyun Yun * SangJin Kim * HyunGoo Kang * * Permission is hereby granted, free of charge, to any person obtaining a copy of * this software and associated documentation files (the "Software"), to deal in * the Software without restriction, including without limitation the rights to * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies * of the Software, and to permit persons to whom the Software is furnished to do * so, subject to the following conditions: * * The above copyright notice and this permission notice shall be included in all * copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE * SOFTWARE. * * Contributors: * - S-Core Co., Ltd * */ #include "es2front.h" void GL_APIENTRY ES2ENTRY(DrawArrays)(GLenum mode, GLint first, GLsizei count) { GLint iArrayBufferBinding; GLvoid* pNewArea; GLchar* pFixedBase; GLfloat* pFloat; int i, j; GLboolean bSpecial = (CCV(pVertexAttrib[0].bEnabled) == GL_FALSE) && (CCV(pVertexAttrib[1].bEnabled) == GL_TRUE); if (mode < 0 || GL_TRIANGLE_FAN < mode) { ES2INTER(SetError)(GL_INVALID_ENUM); return; } if (count < 0) { ES2INTER(SetError)(GL_INVALID_VALUE); return; } else if (count == 0) { return; } FNPTR(GetIntegerv)(GL_ARRAY_BUFFER_BINDING, &iArrayBufferBinding); FNPTR(BindBuffer)(GL_ARRAY_BUFFER, 0); for (i = 0; i < CCV(nMaxVertexAttribs); i++) { register struct VertexAttribUnit* pVertexAttrib = &(CCV(pVertexAttrib[i])); if (pVertexAttrib->bEnabled == GL_FALSE) continue; if (i == 1 && bSpecial == GL_TRUE && pVertexAttrib->eType != GL_FIXED) { FNPTR(BindBuffer)(GL_ARRAY_BUFFER, pVertexAttrib->uBufferBinding); FNPTR(VertexAttribPointer)(0, pVertexAttrib->iSize, pVertexAttrib->eType, pVertexAttrib->bNormalized, pVertexAttrib->uStride, pVertexAttrib->pData); FNPTR(BindBuffer)(GL_ARRAY_BUFFER, 0); } if (pVertexAttrib->eType != GL_FIXED) continue; if (pVertexAttrib->uBufferBinding != 0) { register GLuint uBuffer = pVertexAttrib->uBufferBinding; register struct BufferObjectUnit* pBufferObject = &CCV(pBufferObject[uBuffer]); #if defined(USE_CONVERTED) register GLubyte* pConverted = (GLubyte*)(pBufferObject->pConverted) + (GLsizei)(pVertexAttrib->pData); FNPTR(BindBuffer)(GL_ARRAY_BUFFER, 0); FNPTR(VertexAttribPointer)(i, pVertexAttrib->iSize, GL_FLOAT, pVertexAttrib->bNormalized, pVertexAttrib->uStride, pConverted); if (i == 1 && bSpecial == GL_TRUE) { FNPTR(VertexAttribPointer)(0, pVertexAttrib->iSize, GL_FLOAT, pVertexAttrib->bNormalized, pVertexAttrib->uStride, pConverted); } #else register GLubyte* pConverted = (GLubyte*)pVertexAttrib->pData + pBufferObject->uOffset; FNPTR(BindBuffer)(GL_ARRAY_BUFFER, uBuffer); FNPTR(VertexAttribPointer)(i, pVertexAttrib->iSize, GL_FLOAT, pVertexAttrib->bNormalized, pVertexAttrib->uStride, pConverted); if (i == 1 && bSpecial == GL_TRUE) { FNPTR(VertexAttribPointer)(0, pVertexAttrib->iSize, GL_FLOAT, pVertexAttrib->bNormalized, pVertexAttrib->uStride, pConverted); } FNPTR(BindBuffer)(GL_ARRAY_BUFFER, 0); #endif } else { pNewArea = realloc(pVertexAttrib->pConverted, pVertexAttrib->iSize * count * sizeof(GLfixed)); if (pNewArea == NULL) { ES2INTER(SetError)(GL_OUT_OF_MEMORY); FNPTR(BindBuffer)(GL_ARRAY_BUFFER, iArrayBufferBinding); return; } pVertexAttrib->pConverted = pNewArea; pFixedBase = (GLchar*)(pVertexAttrib->pData) + first * pVertexAttrib->uStride; pFloat = (GLfloat*)(pNewArea); for (j = first; j < first + count; j++) { int k = pVertexAttrib->iSize; GLfixed* pFixed = (GLfixed*)(pFixedBase); while (k--) { register GLfixed xValue = *pFixed++; register GLfloat fValue = fixed_to_float(xValue); *pFloat++ = fValue; } pFixedBase += pVertexAttrib->uStride; } FNPTR(VertexAttribPointer)(i, pVertexAttrib->iSize, GL_FLOAT, pVertexAttrib->bNormalized, pVertexAttrib->iSize * sizeof(GLfixed), (GLvoid*)((GLubyte*)(pVertexAttrib->pConverted) - first * pVertexAttrib->uStride)); if (i == 1 && bSpecial == GL_TRUE) { FNPTR(VertexAttribPointer)(0, pVertexAttrib->iSize, GL_FLOAT, pVertexAttrib->bNormalized, pVertexAttrib->iSize * sizeof(GLfixed), (GLvoid*)((GLubyte*)(pVertexAttrib->pConverted) - first * pVertexAttrib->uStride)); } } } if (bSpecial == GL_TRUE) { FNPTR(EnableVertexAttribArray)(0); } FNPTR(BindBuffer)(GL_ARRAY_BUFFER, iArrayBufferBinding); FNPTR(DrawArrays)(mode, first, count); if (bSpecial == GL_TRUE) { FNPTR(DisableVertexAttribArray)(0); } }