summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--doc/filter_design.txt19
-rw-r--r--libavfilter/avfilter.c10
-rw-r--r--libavfilter/avfilter.h6
-rw-r--r--libavfilter/internal.h13
4 files changed, 18 insertions, 30 deletions
diff --git a/doc/filter_design.txt b/doc/filter_design.txt
index d784d8471e..e8a7c53ee9 100644
--- a/doc/filter_design.txt
+++ b/doc/filter_design.txt
@@ -232,7 +232,8 @@ Frame scheduling
one of its inputs, repeatedly until at least one frame has been pushed.
Return values:
- if request_frame could produce a frame, it should return 0;
+ if request_frame could produce a frame, or at least make progress
+ towards producing a frame, it should return 0;
if it could not for temporary reasons, it should return AVERROR(EAGAIN);
if it could not because there are no more frames, it should return
AVERROR_EOF.
@@ -244,20 +245,18 @@ Frame scheduling
push_one_frame();
return 0;
}
- while (!frame_pushed) {
- input = input_where_a_frame_is_most_needed();
- ret = ff_request_frame(input);
- if (ret == AVERROR_EOF) {
- process_eof_on_input();
- } else if (ret < 0) {
- return ret;
- }
+ input = input_where_a_frame_is_most_needed();
+ ret = ff_request_frame(input);
+ if (ret == AVERROR_EOF) {
+ process_eof_on_input();
+ } else if (ret < 0) {
+ return ret;
}
return 0;
Note that, except for filters that can have queued frames, request_frame
does not push frames: it requests them to its input, and as a reaction,
- the filter_frame method will be called and do the work.
+ the filter_frame method possibly will be called and do the work.
Legacy API
==========
diff --git a/libavfilter/avfilter.c b/libavfilter/avfilter.c
index 7da6cf2643..b9fadb3d59 100644
--- a/libavfilter/avfilter.c
+++ b/libavfilter/avfilter.c
@@ -347,9 +347,7 @@ int ff_request_frame(AVFilterLink *link)
if (link->closed)
return AVERROR_EOF;
- av_assert0(!link->frame_requested);
- link->frame_requested = 1;
- while (link->frame_requested) {
+ // TODO reindent
if (link->srcpad->request_frame)
ret = link->srcpad->request_frame(link);
else if (link->src->inputs[0])
@@ -360,14 +358,9 @@ int ff_request_frame(AVFilterLink *link)
ret = ff_filter_frame_framed(link, pbuf);
}
if (ret < 0) {
- link->frame_requested = 0;
if (ret == AVERROR_EOF)
link->closed = 1;
- } else {
- av_assert0(!link->frame_requested ||
- link->flags & FF_LINK_FLAG_REQUEST_LOOP);
}
- }
return ret;
}
@@ -1088,7 +1081,6 @@ static int ff_filter_frame_framed(AVFilterLink *link, AVFrame *frame)
}
ret = filter_frame(link, out);
link->frame_count++;
- link->frame_requested = 0;
ff_update_link_current_pts(link, pts);
return ret;
diff --git a/libavfilter/avfilter.h b/libavfilter/avfilter.h
index 642aa834ab..5d4cd6ce12 100644
--- a/libavfilter/avfilter.h
+++ b/libavfilter/avfilter.h
@@ -500,12 +500,6 @@ struct AVFilterLink {
int channels;
/**
- * True if a frame is being requested on the link.
- * Used internally by the framework.
- */
- unsigned frame_requested;
-
- /**
* Link processing flags.
*/
unsigned flags;
diff --git a/libavfilter/internal.h b/libavfilter/internal.h
index 7816654010..1454112433 100644
--- a/libavfilter/internal.h
+++ b/libavfilter/internal.h
@@ -102,9 +102,9 @@ struct AVFilterPad {
int (*poll_frame)(AVFilterLink *link);
/**
- * Frame request callback. A call to this should result in at least one
- * frame being output over the given link. This should return zero on
- * success, and another value on error.
+ * Frame request callback. A call to this should result in some progress
+ * towards producing output over the given link. This should return zero
+ * on success, and another value on error.
*
* Output pads only.
*/
@@ -291,8 +291,11 @@ int ff_poll_frame(AVFilterLink *link);
* caller (generally eventually a user application) as this step may (but does
* not have to be) necessary to provide the input with the next frame.
*
- * If a request is successful then the filter_frame() function will be called
- * at least once before ff_request_frame() returns
+ * If a request is successful then some progress has been made towards
+ * providing a frame on the link (through ff_filter_frame()). A filter that
+ * needs several frames to produce one is allowed to return success if one
+ * more frame has been processed but no output has been produced yet. A
+ * filter is also allowed to simply forward a success return value.
*
* @param link the input link
* @return zero on success