blob: bf6a7e74659fd6adb9439793e11e986858079c50 [file] [log] [blame]
PUSH vs PULL
(This is a writedown of ideas I plan to update whenever I find issues. This
should be fleshed out when doing the threadsafety / buffer passing changes.)
GStreamer allows 3 different forms of elements:
- loopbased:
Loopbased elements may push and pull from every pad however they want. They're
therefore heaviest on the scheduler and for latency or similar considerations.
- chainbased:
Chainbased elements have one sinkpad. Data gets pushed into a function attached
to the pad. => PUSH based
- getbased:
Getbased elements have no sinkpads. Every sourcepad has a getfunction that
produces data on request. => PULL based
The current problem is that PUSH and PULL based elements are quite limited in
what they may or may not do (especially PULL based elements). Some libraries
elements link to might also expect the architecture around them to work in a
specific way (libogg requires the ogg input to be pull-based, JACK is PULL-based
on sinks and PUSH-based on sinks). This often requires costly wrapping.
Inside a scheduler cothread switches can be avoided (which makes the pipeline
faster and scheduling less error-prone) if a PUSH-based element is connected on
the push-side of the pipeline. (Same goes with PULL-based on the pull-side). So
a pipeline with elements like "pull-pull-loop-push" works without cothread
switches while a pipeline like "push-loop-pull" needs 2. Even "push-pull" needs
one.
I'm under the impression that push-vs-pull is often best decided by the
application in use. (Video players probably prefer PULL because they display on
demand, live recorders prefer PUSH.) Since many elements probably don't care if
they're PUSH or PULL based it would be nice if an element could implement both
and use whatever suits better. (The code to achieve this should obviously be
abstracted into superclasses like videofilter.)
references:
MPlayer (http://www.mplayerhq.hu) - push-based architecture on version 1,
switching to PULL-based on version 2.