4

I've been having a very weird issue with my project's texture generation. The first mipmapped texture works flawlessly but the next ones only draw the first level. While debugging I suddenly came to a hack that fixes it:

glGenTextures(1, &texture->textureID);
glBindTexture(GL_TEXTURE_2D, texture->textureID);

glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);

glTexStorage2D(GL_TEXTURE_2D, 10, GL_RGBA8, width, height);
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, width, height, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
glGenerateMipmap(GL_TEXTURE_2D);
assert(glGetError() == GL_NO_ERROR);    // Mipmapping fails if glGetError is not here

glBindTexture(GL_TEXTURE_2D, 0);

Why on earth is this only working when a glGetError (which, as you can see with this assert, is ALWAYS returning GL_NO_ERROR) function is called after the glGenerateMimap? Why does it have anything to do with it?

I'm currently using a GeForce GTX 670 with the latest GeForce 340.52 driver

Edit: A couple of images might help

With glGetError():

enter image description here

Without glGetError():

enter image description here

h4lc0n
  • 2,730
  • 5
  • 29
  • 41
  • What are the values for 'width` and 'height`? In any case, I agree that it looks puzzling. The most likely explanation would be a driver bug. – Reto Koradi Aug 16 '14 at 19:28
  • They are not power of two if that is your question, though my graphics card supports them. Still, I'll give it a go with POT images to see if that makes any difference. – h4lc0n Aug 16 '14 at 19:35
  • I actually wanted to check that they were at least 512, because otherwise specifying 10 levels for `glTexStorage2D()` would be an error. But since you're not getting an error, I figure that the arguments must be fine. – Reto Koradi Aug 16 '14 at 19:39
  • Ah, I see. Yes, they are. I just tried with a couple of 1024x1024 images right now and the same thing happens. I'm going to just assume this is a driver bug for now and re-check when they update again. Thanks anyways – h4lc0n Aug 16 '14 at 19:41

1 Answers1

2

Referring to Is iOS glGenerateMipmap synchronous, or is it possibly asynchronous?, it seems glGenerateMipmaps works asynchronously. My project uses shared contexts to create shaders, textures and meshes (sorry if I didn't mention this, I didn't think it would matter).

The thing is, whenever the texture generation finished the "textures generated" flag was risen and the shared context would get destroyed, it seems the last glGenerateMipmap was therefore not getting flushed through the pipeline. The call to glGetError needs to flush the operations from the pipeline to see whether there's been any error to report, and this is exactly why it was making everything work flawlessly.

So, in other words, if you're doing something on a separate, shared context, you need to explicitly call glFinish before killing that thread, or some operations will be left undone.

Community
  • 1
  • 1
h4lc0n
  • 2,730
  • 5
  • 29
  • 41