[Mesa-dev] Proper implemtation of glFinish

Michel Dänzer michel at daenzer.net
Tue Jan 4 00:31:25 PST 2011


On Mon, 2011-01-03 at 22:50 +0100, Francisco Jerez wrote: 
> Bob Gleitsmann <rjgleits at bellsouth.net> writes:
> 
> > When trying the demo program copytex for the first time recently, I noticed 
> > pathological behavior: after running for a long time it asserted out and 
> > locked up X. Investigation showed this to be due to the glFinish function 
> > acting like glFlush and not waiting as it is supposed to for completion of 
> > whatever commands had been issued. I took up the task of remedying this.
> 
> Thank you for having a look at this, I've been meaning to fix it for a while.
> 
> > There are, as usual, a variety of different ways of doing so. Influenced by
> > the current gallium code, I planned a separate call to the kernel to wait
> > for the fence created by the pushbuf flush ioctl to complete. After
> > completing the implementation in this way, it occurred to me that it would
> > be more economical to modify the pushbuf flush ioctl call with a flag to
> > indicate whether it should wait for completion or not. This would require
> > modifying the FIRE_RING inline which appears in numerous places. Perhaps my
> > original plan is adequate.  The code changes required for the original plan
> > involve mesa, drm, and the kernel.
> 
> ATM the nouveau DRM API doesn't let you wait on a fence (it doesn't even have
> the concept of "fence"), instead, you're supposed to wait for a specific
> buffer using the CPU_PREP IOCTL. I think the simplest way to get nouveau an
> implementation of the screen fence stuff would be something like:
> 
> | struct nouveau_fence {
> |       struct nouveau_bo *bo;
> |       boolean signalled;
> | }
> 
> IOW, a fence would just hold a reference to a buffer object being rendered to
> when the fence was created. nouveau_screen_fence_finish() would call
> nouveau_bo_map()/unmap() with the BO as argument to make sure the fenced
> rendering has landed. The BO selection process would look a bit like
> r300_finish() and it could be done from nvfx/nv50_context.c.

Beware that this approach will wait for *all* rendering to (and possibly
from) that BO to finish, whereas the intended semantics are to wait only
for the operations up to the point when the fence was created. This
distinction probably doesn't matter for the GL state tracker so far but
I think this will change sooner or later, and it already matters at
least for the xorg state tracker (for the swap/dirty throttling).


-- 
Earthling Michel Dänzer           |                http://www.vmware.com
Libre software enthusiast         |          Debian, X and DRI developer


More information about the mesa-dev mailing list