Re: A possible problem with an external compositing manager

Keith Whitwell <keith-CdwZJljFklH+2FeEXyspIVaTQe2KTcn/@public.gmane.org>
Newsgroups gmane.comp.freedesktop.xserver
Message-ID <[email protected]>
Soeren Sandmann wrote:
> Keith Packard <[email protected]> writes:
> 
> 
>>Around 13 o'clock on Nov 12, Soeren Sandmann wrote:
>>
>>
>>>I thought of a potential problem with having all drawing routed though
>>>an external compositing manager: Applications can no longer know for
>>>sure that their drawing has actually reached the screen.
>>
>>I hadn't thought of this, but it's certainly a valid point.  I can think 
>>of several solutions, but none which is both efficient and compatible with 
>>existing mechanisms.
>>
>>I addressed this in the shadow frame buffer code by special casing 
>>GetImage to sync contents to the screen before returning the data; we 
>>can't really do that in this case without a lot of hacks.
> 
> 
> It is not GetImage I am worried about. It is the fact that
> applications don't know how when their drawing reaches the screen.
> 
> An application that wants to draw a frame of an animation as often as
> possible can currently do this:
> 
> (A)     Draw frame
>         XSync()
>         Draw frame
>         XSync()
>         ...
> 
> Each XSync() has the effect of waiting until the server has actually
> drawn the previous frame. This:

XSync() only waits until the X server has consumed all of the protocol, not 
until drawing has actually percolated down through the DDX driver, out into 
hardware and emerged on the screen.

To some extent it's up to the X server, driver, etc to ensure that the 
hardware doesn't get too far behind the protocol.

So, your current application isn't guarenteed of this as it stands, and the 
new extension doesn't seem to change anything.  (Though it's implication might...)


> (B)     Draw frame
>         Draw frame
>         Draw frame
>         Draw frame
>         ...
> 
> would swamp the X server with updates. Note this is an animation that
> at any point in time has a frame it wants drawn, a continuous
> animation, as opposed to an animation with a discrete set of frames
> like a video playback.
> 
> If you try (A) in the presence of a compositing manager, each XSync()
> would only make sure that a DamageNotify had been sent to the
> compositing manager, not that the pixels were actually drawn to the
> screen.

It would presumably mean that the pixels have been drawn to a backbuffer 
somewhere (or strictly, the protocol causing pixels to be drawn to a 
backbuffer had been processed).

  This means the application would try to generate too many
> frames which is a waste of CPU that would be taken away from the
> composting manager if they were on the same computer.

Is the problem that there is no equivalent of 'glXSwapBuffers()' in this 
extension, to mark the boundary between frames? (I haven't read it closely 
enough to know).  How does the compositor know when an animated window is in a 
state suitable to be composited to the frontbuffer?


One problem with XSync() even in regular usage is that it forces the 
application to stall while the X server finishes processing the current frame. 
  That's ok on a uniprocessor with local rendering, but in other situations 
it's a wasteful way to synchronize.  You'd much rather have some mechanism 
that lets the animation applicaiton continue calculating/rendering at full 
speed, producing a steady stream of commands for the Xserver and hardware to 
process, and that only if the application started getting ahead of the X 
server would it be slowed down/throttled.  Or, a more sophisticated mechanism 
where synchronization points are emitted and explicitly retired.

GL drivers deal with runaway applications in a couple of ways.  In unextended 
GL, for double-buffered applications at least, it is easy to detect runaway 
situations by emitting breadcrumbs to hardware each time SwapBuffers is 
called.  If the hardware hasn't finished displaying the frame before last (ie 
the application is about to go two frames ahead), the driver should go to 
sleep until the hardware catches up.  This isn't specified in the spec 
anywhere, but is a practical necessity and seems to be universally implemented 
(in large part due to efforts from people like John Carmack).

There are extensions that place the synchronization primitives more directly 
in the control of the application.  Here's one:

	http://oss.sgi.com/projects/ogl-sample/registry/NV/fence.txt

Keith
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.