Question

I'm not trying to stream or anything, I just want to speed up my file loading code by loading vertex and index data directly into OpenGL's buffer instead of having to put it in an intermediate buffer first. Here's the code that grabs the pointer:

void* VertexArray::beginIndexLoad(GLenum indexFormat, unsigned int indexCount)
{
    if (vao == 0)
        return NULL;

    bindArray();

    glGenBuffers(1, &ibo);
    glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, ibo);
    glBufferData(GL_ELEMENT_ARRAY_BUFFER, indexSize(indexFormat) * indexCount, NULL, GL_STATIC_DRAW);

    iformat = indexFormat;
    icount = indexCount;

    GLenum err = glGetError();
    printf("%i\n", err);

    void* ptr = glMapBuffer(GL_ELEMENT_ARRAY_BUFFER, GL_WRITE_ONLY);

    err = glGetError();
    printf("%i\n", err);

    unbindArray();

    return ptr;
}

Problem is, this returns NULL. What's worse, just before I do something similar with GL_ARRAY_BUFFER, and I get a perfectly valid pointer. Why does this fail, while the other succeeds?

The first glGetError returns 1280 (GL_INVALID_ENUM). The second glGetError returns 1285(GL_OUT_OF_MEMORY). I know it's not actually out of memory because uploading the exact same data normally via glBufferData works fine.

Maybe I'm just handling vertex arrays wrong?

(ps. I asked this on gamedev stack exchange and got nothing. Re-posting here to try to figure it out)

No correct solution

OTHER TIPS

First and foremost your error checking code is wrong. You must call glGetError in a loop until it returns GL_NO_ERROR.

Regarding the GL_OUT_OF_MEMORY error code: It can also mean out of address space, which can easily happen if a large contiguous area of virtual address space is requested from the OS, but the process' address space is so much fragmented that no chunk that size is available (even if the total amount of free address space would suffice).

This has become the bane of 32 bit systems. A simple remedy is to use a 64 bit system. If you're stuck with a 32 bit plattform you'll have to defragment your address space (which is not trivial).

If I were you I would try the following:

  • Replace GL_STATIC_DRAW with GL_DYNAMIC_DRAW
  • Make sure that indexSize(indexFormat) * indexCount produces the size you are expecting
  • Try using glMapBufferRange instead of glMapBuffer, something along the line of glMapBufferRange(GL_ELEMENT_ARRAY_BUFFER, 0, yourBufferSize, GL_MAP_WRITE_BIT | GL_MAP_INVALIDATE_BUFFER_BIT);
  • Check that ibo is of type GLuint

EDIT: fwiw, I would get a gDEBugger and set a breakpoint to break when there is an OpenGL error.

I solved the problem. I was passing in indexSize(header.indexFormat) when I should have been passing in header.indexFormat. I feel like an idiot now, and I'm sorry for wasting everyone's time.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top