summary |
shortlog |
log |
commit | commitdiff |
tree
raw |
patch |
inline | side by side (from parent 1:
88add60)
I found very similar workaround code for this bug in Chromium,
with the following comment:
// Workaround for Mac driver bug. In the large scheme of things setting
// glTexParamter twice for glGenerateMipmap is probably not a lage performance
// hit so there's probably no need to make this conditional. The bug appears
// to be that if the filtering mode is set to something that doesn't require
// mipmaps for rendering, or is never set to something other than the default,
// then glGenerateMipmap misbehaves.
Going back all the way to the point in which this code was written,
it is indeed true; we called glGenerateMipmap(), and then right afterwards
set the mode to GL_LINEAR_MIPMAP_NEAREST. Since then, the code has been
reorganized and moved around a lot, and now we set the mode long before
the first call to glGenerateMipmap(), and thus we can retire the hack;
simply generate mipmaps on-demand, and that's the end of it. I tested
with the Mesa 8.0.x version where I originally saw this bug, and it passes
flat_input_test without any problems (well, actually all tests except
the tests for deconvolution sharpen, whose shaders are too big for it).
This is nice not only because it gives us a less hacky structure, but also
because GL_GENERATE_MIPMAPS is a nightmare for the driver to handle;
several edge conditions are tricky, from what I've been told.
check_error();
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, needs_mipmaps ? GL_LINEAR_MIPMAP_NEAREST : GL_LINEAR);
check_error();
check_error();
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, needs_mipmaps ? GL_LINEAR_MIPMAP_NEAREST : GL_LINEAR);
check_error();
- // Intel/Mesa seems to have a broken glGenerateMipmap() for non-FBO textures, so do it here
- // instead of calling glGenerateMipmap().
- glTexParameteri(GL_TEXTURE_2D, GL_GENERATE_MIPMAP, needs_mipmaps ? GL_TRUE : GL_FALSE);
- check_error();
glTexImage2D(GL_TEXTURE_2D, 0, internal_format, width, height, 0, format, type, NULL);
check_error();
glPixelStorei(GL_UNPACK_ROW_LENGTH, 0);
glTexImage2D(GL_TEXTURE_2D, 0, internal_format, width, height, 0, format, type, NULL);
check_error();
glPixelStorei(GL_UNPACK_ROW_LENGTH, 0);
check_error();
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, width, height, format, type, pixel_data);
check_error();
check_error();
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, width, height, format, type, pixel_data);
check_error();
+ if (needs_mipmaps) {
+ glGenerateMipmap(GL_TEXTURE_2D);
+ check_error();
+ }
glPixelStorei(GL_UNPACK_ROW_LENGTH, 0);
check_error();
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glPixelStorei(GL_UNPACK_ROW_LENGTH, 0);
check_error();
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);