void * PACKSPU_APIENTRY packspu_MapBufferARB( GLenum target, GLenum access ) { GET_CONTEXT(ctx); void *buffer; CRBufferObject *pBufObj; CRASSERT(GL_TRUE == ctx->clientState->bufferobject.retainBufferData); buffer = crStateMapBufferARB(target, access); #ifdef CR_ARB_pixel_buffer_object if (buffer) { pBufObj = crStateGetBoundBufferObject(target, &ctx->clientState->bufferobject); CRASSERT(pBufObj); if (pBufObj->bResyncOnRead && access != GL_WRITE_ONLY_ARB) { /*fetch data from host side*/ packspu_GetHostBufferSubDataARB(target, 0, pBufObj->size, buffer); } } #endif return buffer; }
void STATE_APIENTRY crStateGetBufferPointervARB(GLenum target, GLenum pname, GLvoid **params) { CRContext *g = GetCurrentContext(); CRBufferObjectState *b = &g->bufferobject; CRBufferObject *obj; FLUSH(); if (g->current.inBeginEnd) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glGetBufferPointervARB called in begin/end"); return; } obj = crStateGetBoundBufferObject(target, b); if (!obj) { crStateError(__LINE__, __FILE__, GL_INVALID_ENUM, "glGetBufferPointervARB(target)"); return; } if (pname != GL_BUFFER_MAP_POINTER_ARB) { crStateError(__LINE__, __FILE__, GL_INVALID_ENUM, "glGetBufferPointervARB(pname)"); return; } *params = obj->pointer; }
void STATE_APIENTRY crStateBufferSubDataARB(GLenum target, GLintptrARB offset, GLsizeiptrARB size, const GLvoid * data) { CRContext *g = GetCurrentContext(); CRBufferObjectState *b = &g->bufferobject; CRBufferObject *obj; CRStateBits *sb = GetCurrentBits(); CRBufferObjectBits *bb = &sb->bufferobject; FLUSH(); if (g->current.inBeginEnd) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glBufferSubDataARB called in begin/end"); return; } obj = crStateGetBoundBufferObject(target, b); if (!obj) { crStateError(__LINE__, __FILE__, GL_INVALID_ENUM, "glBufferSubDataARB(target)"); return; } if (obj->id == 0) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glBufferSubDataARB"); return; } if (obj->pointer) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glBufferSubDataARB(buffer is mapped)"); return; } if (size < 0 || offset < 0 || (unsigned int)offset + size > obj->size) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glBufferSubDataARB(bad offset and/or size)"); return; } if (b->retainBufferData && obj->data) { crMemcpy((char *) obj->data + offset, data, size); } DIRTY(bb->dirty, g->neg_bitid); DIRTY(obj->dirty, g->neg_bitid); /* grow dirty region */ if (offset + size > obj->dirtyStart + obj->dirtyLength) obj->dirtyLength = offset + size; if (offset < obj->dirtyStart) obj->dirtyStart = offset; }
GLboolean STATE_APIENTRY crStateUnmapBufferARB(GLenum target) { CRContext *g = GetCurrentContext(); CRBufferObjectState *b = &g->bufferobject; CRBufferObject *obj; CRStateBits *sb = GetCurrentBits(); CRBufferObjectBits *bb = &sb->bufferobject; FLUSH(); if (g->current.inBeginEnd) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glUnmapBufferARB called in begin/end"); return GL_FALSE; } obj = crStateGetBoundBufferObject(target, b); if (!obj) { crStateError(__LINE__, __FILE__, GL_INVALID_ENUM, "glUnmapBufferARB(target)"); return GL_FALSE; } if (obj->id == 0) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glUnmapBufferARB"); return GL_FALSE; } if (!obj->pointer) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glUnmapBufferARB"); return GL_FALSE; } obj->pointer = NULL; if (obj->access != GL_READ_ONLY_ARB) { /* the data was most likely modified */ DIRTY(bb->dirty, g->neg_bitid); DIRTY(obj->dirty, g->neg_bitid); obj->dirtyStart = 0; obj->dirtyLength = obj->size; } return GL_TRUE; }
void PACKSPU_APIENTRY packspu_GetBufferSubDataARB( GLenum target, GLintptrARB offset, GLsizeiptrARB size, void * data ) { GET_CONTEXT(ctx); #ifdef CR_ARB_pixel_buffer_object CRBufferObject *pBufObj; pBufObj = crStateGetBoundBufferObject(target, &ctx->clientState->bufferobject); if (pBufObj && pBufObj->bResyncOnRead) { packspu_GetHostBufferSubDataARB(target, offset, size, data); return; } #endif crStateGetBufferSubDataARB(target, offset, size, data); }
void * STATE_APIENTRY crStateMapBufferARB(GLenum target, GLenum access) { CRContext *g = GetCurrentContext(); CRBufferObjectState *b = &g->bufferobject; CRBufferObject *obj; FLUSH(); if (g->current.inBeginEnd) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glMapBufferARB called in begin/end"); return NULL; } obj = crStateGetBoundBufferObject(target, b); if (!obj) { crStateError(__LINE__, __FILE__, GL_INVALID_ENUM, "glMapBufferARB(target)"); return NULL; } if (obj->id == 0) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glMapBufferARB"); return GL_FALSE; } switch (access) { case GL_READ_ONLY_ARB: case GL_WRITE_ONLY_ARB: case GL_READ_WRITE_ARB: obj->access = access; break; default: crStateError(__LINE__, __FILE__, GL_INVALID_ENUM, "glMapBufferARB(access)"); return NULL; } if (b->retainBufferData && obj->data) obj->pointer = obj->data; return obj->pointer; }
void STATE_APIENTRY crStateGetBufferSubDataARB(GLenum target, GLintptrARB offset, GLsizeiptrARB size, void * data) { CRContext *g = GetCurrentContext(); CRBufferObjectState *b = &g->bufferobject; CRBufferObject *obj; FLUSH(); if (g->current.inBeginEnd) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glGetBufferSubDataARB called in begin/end"); return; } obj = crStateGetBoundBufferObject(target, b); if (!obj) { crStateError(__LINE__, __FILE__, GL_INVALID_ENUM, "glGetBufferSubDataARB(target)"); return; } if (obj->id == 0) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glGetBufferSubDataARB"); return; } if (obj->pointer) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glGetBufferSubDataARB(buffer is mapped)"); return; } if (size < 0 || offset < 0 || (unsigned int)offset + size > obj->size) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glGetBufferSubDataARB(bad offset and/or size)"); return; } if (b->retainBufferData && obj->data) { crMemcpy(data, (char *) obj->data + offset, size); } }
GLboolean PACKSPU_APIENTRY packspu_UnmapBufferARB( GLenum target ) { GET_CONTEXT(ctx); #if CR_ARB_vertex_buffer_object CRBufferObject *bufObj; bufObj = crStateGetBoundBufferObject(target, &ctx->clientState->bufferobject); /* send new buffer contents to server */ crPackBufferDataARB( target, bufObj->size, bufObj->pointer, bufObj->usage ); #endif CRASSERT(GL_TRUE == ctx->clientState->bufferobject.retainBufferData); crStateUnmapBufferARB( target ); return GL_TRUE; }
void STATE_APIENTRY crStateGetBufferParameterivARB(GLenum target, GLenum pname, GLint *params) { CRContext *g = GetCurrentContext(); CRBufferObjectState *b = &g->bufferobject; CRBufferObject *obj; FLUSH(); if (g->current.inBeginEnd) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glGetBufferParameterivARB called in begin/end"); return; } obj = crStateGetBoundBufferObject(target, b); if (!obj) { crStateError(__LINE__, __FILE__, GL_INVALID_ENUM, "glGetBufferParameterivARB(target)"); return; } switch (pname) { case GL_BUFFER_SIZE_ARB: *params = obj->size; break; case GL_BUFFER_USAGE_ARB: *params = obj->usage; break; case GL_BUFFER_ACCESS_ARB: *params = obj->access; break; case GL_BUFFER_MAPPED_ARB: *params = (obj->pointer != NULL); break; default: crStateError(__LINE__, __FILE__, GL_INVALID_ENUM, "glGetBufferParameterivARB(pname)"); return; } }
void STATE_APIENTRY crStateBindBufferARB (GLenum target, GLuint buffer) { CRContext *g = GetCurrentContext(); CRBufferObjectState *b = &(g->bufferobject); CRStateBits *sb = GetCurrentBits(); CRBufferObjectBits *bb = &(sb->bufferobject); CRBufferObject *oldObj, *newObj; if (g->current.inBeginEnd) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glBindBufferARB called in begin/end"); return; } FLUSH(); oldObj = crStateGetBoundBufferObject(target, b); if (!oldObj) { crStateError(__LINE__, __FILE__, GL_INVALID_ENUM, "glBindBufferARB(target)"); return; } if (buffer == 0) { newObj = b->nullBuffer; } else { newObj = (CRBufferObject *) crHashtableSearch(g->shared->buffersTable, buffer); if (!newObj) { CRSTATE_CHECKERR(!crHashtableIsKeyUsed(g->shared->buffersTable, buffer), GL_INVALID_OPERATION, "name is not a buffer object"); newObj = AllocBufferObject(buffer); CRSTATE_CHECKERR(!newObj, GL_OUT_OF_MEMORY, "glBindBuffer"); #ifndef IN_GUEST diff_api.GenBuffersARB(1, &newObj->hwid); if (!newObj->hwid) { crWarning("GenBuffersARB failed!"); crFree(newObj); return; } #endif crHashtableAdd( g->shared->buffersTable, buffer, newObj ); } CR_STATE_SHAREDOBJ_USAGE_SET(newObj, g); } newObj->refCount++; oldObj->refCount--; switch (target) { case GL_ARRAY_BUFFER_ARB: b->arrayBuffer = newObj; DIRTY(bb->dirty, g->neg_bitid); DIRTY(bb->arrayBinding, g->neg_bitid); break; case GL_ELEMENT_ARRAY_BUFFER_ARB: b->elementsBuffer = newObj; DIRTY(bb->dirty, g->neg_bitid); DIRTY(bb->elementsBinding, g->neg_bitid); break; #ifdef CR_ARB_pixel_buffer_object case GL_PIXEL_PACK_BUFFER_ARB: b->packBuffer = newObj; DIRTY(bb->dirty, g->neg_bitid); DIRTY(bb->packBinding, g->neg_bitid); break; case GL_PIXEL_UNPACK_BUFFER_ARB: b->unpackBuffer = newObj; DIRTY(bb->dirty, g->neg_bitid); DIRTY(bb->unpackBinding, g->neg_bitid); break; #endif default: /*can't get here*/ CRASSERT(false); return; } if (oldObj->refCount <= 0) { /*we shouldn't reach this point*/ CRASSERT(false); crHashtableDelete(g->shared->buffersTable, (unsigned long) oldObj->id, crStateFreeBufferObject); } #ifdef IN_GUEST if (target == GL_PIXEL_PACK_BUFFER_ARB) { newObj->bResyncOnRead = GL_TRUE; } #endif }
void STATE_APIENTRY crStateBufferDataARB(GLenum target, GLsizeiptrARB size, const GLvoid * data, GLenum usage) { CRContext *g = GetCurrentContext(); CRBufferObjectState *b = &g->bufferobject; CRBufferObject *obj; CRStateBits *sb = GetCurrentBits(); CRBufferObjectBits *bb = &sb->bufferobject; FLUSH(); if (g->current.inBeginEnd) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glBufferDataARB called in begin/end"); return; } if (size < 0) { crStateError(__LINE__, __FILE__, GL_INVALID_VALUE, "glBufferDataARB(size < 0)"); return; } switch (usage) { case GL_STREAM_DRAW_ARB: case GL_STREAM_READ_ARB: case GL_STREAM_COPY_ARB: case GL_STATIC_DRAW_ARB: case GL_STATIC_READ_ARB: case GL_STATIC_COPY_ARB: case GL_DYNAMIC_DRAW_ARB: case GL_DYNAMIC_READ_ARB: case GL_DYNAMIC_COPY_ARB: /* OK */ break; default: crStateError(__LINE__, __FILE__, GL_INVALID_ENUM, "glBufferDataARB(usage)"); return; } obj = crStateGetBoundBufferObject(target, b); if (!obj) { crStateError(__LINE__, __FILE__, GL_INVALID_ENUM, "glBufferDataARB(target)"); return; } if (obj->id == 0) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glBufferDataARB"); return; } if (obj->pointer) { crStateError(__LINE__, __FILE__, GL_INVALID_OPERATION, "glBufferDataARB(buffer is mapped)"); return; } obj->usage = usage; obj->size = size; /* The user of the state tracker should set the retainBufferData field * during context initialization, if needed. */ if (b->retainBufferData) { if (obj->data) { crFree(obj->data); } obj->data = crAlloc(size); if (!obj->data) { crStateError(__LINE__, __FILE__, GL_OUT_OF_MEMORY, "glBufferDataARB"); return; } if (data) crMemcpy(obj->data, data, size); } DIRTY(bb->dirty, g->neg_bitid); DIRTY(obj->dirty, g->neg_bitid); obj->dirtyStart = 0; obj->dirtyLength = size; }