<div dir="ltr"><div>I started this discussion with just some of the Intel folks, and Eric suggested I bring it to the mesa-dev list.<br><br></div>The short version is: in my efforts to implement fast color clears on Intel hardware, I've uncovered some problems with the fbo-sys-blit piglit test, which I've traced to 3 bugs.  I could use some help with bug (2) below, which I suspect is a bug in the X server. <br>
<div><div><br><div class="gmail_quote">---------- Forwarded message (footnotes added) ----------<div dir="ltr"><div><br></div>First of all, a brief summary of what fbo-sys-blit's piglit_display() does:<br><div><br></div>
<div>a. Clear the back buffer to green.<br></div><div>b. Copy the back buffer to the front buffer using a blit.<br>
</div><div>c. Clear the back buffer to red.<br></div><div>d. Read the contents of the front buffer to verify that it's green.<br></div><div><br>I've found three bugs:<br><br></div><div>1. Background: when a fake front buffer is in use, if Mesa requests the front buffer (using screen->dri2.loader->getBuffersWithFormat()), the X server copies the real front buffer to the fake front buffer and returns the fake front buffer.  Mesa sometimes makes redundant requests for the front buffer (due to using a single counter to track invalidates for both the front and back buffers), so there's a danger of pending front buffer rendering getting overwritten when the redundant front buffer request occurs.  To work around this problem, intel_update_renderbuffers() sometimes does intel_flush() and intel_flush_front() before calling intel_query_dri2_buffers().  The problem is, it only does the workaround when the front buffer is bound for drawing; it doesn't do it when the front buffer is bound for reading.  As a result, in step (d) above, the fake front buffer gets overwritten with the contents of the real front buffer (which contains garbage).  This is why fbo-sys-blit fails sporadically during automated piglit runs; frequently the garbage happens to be green, but sometimes it doesn't.<br>
<br></div>2. Normally the way intel_prepare_render() finds out whether it needs to call intel_update_renderbuffers() is that it gets an "invalidate" signal from the X server (this is processed by DRI2WireToEvent()).  This happens whenever the window is resized or a buffer swap occurs, but it doesn't consistently happen when the window gets exposed on the screen for the first time (even though this causes new front and back buffers to be allocated*).  Currently, when running in non-"auto" mode, the piglit framework calls piglit_display() once before the window gets exposed, and then again in response to the Expose event.**  Therefore, when running fbo-sys-blit, on the second call to piglit_display(), Mesa sometimes doesn't get the message that there are new buffers, so the clear in step (a) goes to an old garbage buffer.  Mesa decides to query the buffers before executing step (b), so garbage data gets copied from back to front.  This causes fbo-sys-blit to fail sporadically when run manually, even if I fix bug (1) above.***<br>
<div>
<br></div><div>3. intelClear() and brw_clear() set intel->front_buffer_dirty 
before calling intel_prepare_render().  This is wrong: if 
intel_prepare_render() gets a fresh front buffer from the X server, it 
will reset front_buffer_dirty to false, so the front buffer won't get 
properly marked as dirty.  Fortunately intel_prepare_render() also sets 
front_buffer_dirty to true if the front buffer is bound for drawing, 
which means that this bug will only manifest when using glClearBuffer() 
to clear the front buffer while the back buffer is bound (probably very 
rare).  I found this bug by code inspection; I haven't verified it yet.<br><br>I'll submit patches to the list to fix bugs (1) and (3).  I don't know how to tackle bug (2) and I'm hoping someone more knowledgeable about X server internals can have a look.<br>
<br></div><div>*I don't know what code is allocating the new front and back buffers; I just know from examining data in the debugger that it's happened (since the buffer names have changed).  Note that I'm running my tests with a compositing desktop (Gnome 3), so it's possible that this is the compositor's doing.<br>

</div></div>
</div><br></div><div>**Eric pointed out that this is a bug in Piglit, since on non-compositing desktops the front buffer isn't guaranteed to exist until after the Expose event.  I'm hoping to send out patches to fix this Piglit bug soon.  Note: I believe that even on non-compositing desktops, the back buffer is still guaranteed to exist before the Expose event, so the only Piglit tests that need to be fixed to wait for the Expose event are those that access the front buffer, for example fbo-sys-blit.  Please correct me if I have this wrong.<br>
</div><div><br></div><div>***Note that fixing the above Piglit bug won't make bug (2) go away.  In fact it will make bug (2) affect both "-auto" and manual testing (currently it only affects manual testing).  The reason for this is that Mesa queries the back buffer during intelMakeCurrent() (which happens before the Expose event).  So step (a) will always clear the old (defunct) back buffer, and then Mesa will receive the new back buffer just before doing the blit in step (b), and will blit garbage to the front buffer.<br>
</div></div></div>