2 * This file is part of FFmpeg.
4 * FFmpeg is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
9 * FFmpeg is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with FFmpeg; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
21 * Frame multithreading support functions
22 * @see doc/multithreading.txt
32 #include "compat/w32pthreads.h"
34 #include "compat/os2threads.h"
39 #include "pthread_internal.h"
43 #include "libavutil/avassert.h"
44 #include "libavutil/buffer.h"
45 #include "libavutil/common.h"
46 #include "libavutil/cpu.h"
47 #include "libavutil/frame.h"
48 #include "libavutil/internal.h"
49 #include "libavutil/log.h"
50 #include "libavutil/mem.h"
53 * Context used by codec threads and stored in their AVCodecInternal thread_ctx.
55 typedef struct PerThreadContext
{
56 struct FrameThreadContext
*parent
;
60 pthread_cond_t input_cond
; ///< Used to wait for a new packet from the main thread.
61 pthread_cond_t progress_cond
; ///< Used by child threads to wait for progress to change.
62 pthread_cond_t output_cond
; ///< Used by the main thread to wait for frames to finish.
64 pthread_mutex_t mutex
; ///< Mutex used to protect the contents of the PerThreadContext.
65 pthread_mutex_t progress_mutex
; ///< Mutex used to protect frame progress values and progress_cond.
67 AVCodecContext
*avctx
; ///< Context used to decode packets passed to this thread.
69 AVPacket avpkt
; ///< Input packet (for decoding) or output (for encoding).
71 AVFrame
*frame
; ///< Output frame (for decoding) or input (for encoding).
72 int got_frame
; ///< The output of got_picture_ptr from the last avcodec_decode_video() call.
73 int result
; ///< The result of the last codec decode/encode() call.
76 STATE_INPUT_READY
, ///< Set when the thread is awaiting a packet.
77 STATE_SETTING_UP
, ///< Set before the codec has called ff_thread_finish_setup().
78 STATE_GET_BUFFER
, /**<
79 * Set when the codec calls get_buffer().
80 * State is returned to STATE_SETTING_UP afterwards.
82 STATE_GET_FORMAT
, /**<
83 * Set when the codec calls get_format().
84 * State is returned to STATE_SETTING_UP afterwards.
86 STATE_SETUP_FINISHED
///< Set after the codec has called ff_thread_finish_setup().
90 * Array of frames passed to ff_thread_release_buffer().
91 * Frames are released after all threads referencing them are finished.
93 AVFrame
*released_buffers
;
94 int num_released_buffers
;
95 int released_buffers_allocated
;
97 AVFrame
*requested_frame
; ///< AVFrame the codec passed to get_buffer()
98 int requested_flags
; ///< flags passed to get_buffer() for requested_frame
100 const enum AVPixelFormat
*available_formats
; ///< Format array for get_format()
101 enum AVPixelFormat result_format
; ///< get_format() result
105 * Context stored in the client AVCodecInternal thread_ctx.
107 typedef struct FrameThreadContext
{
108 PerThreadContext
*threads
; ///< The contexts for each thread.
109 PerThreadContext
*prev_thread
; ///< The last thread submit_packet() was called on.
111 pthread_mutex_t buffer_mutex
; ///< Mutex used to protect get/release_buffer().
113 int next_decoding
; ///< The next context to submit a packet to.
114 int next_finished
; ///< The next context to return output from.
117 * Set for the first N packets, where N is the number of threads.
118 * While it is set, ff_thread_en/decode_frame won't return any results.
121 int die
; ///< Set when threads should exit.
122 } FrameThreadContext
;
124 #if FF_API_GET_BUFFER
125 #define THREAD_SAFE_CALLBACKS(avctx) \
126 ((avctx)->thread_safe_callbacks || (!(avctx)->get_buffer && (avctx)->get_buffer2 == avcodec_default_get_buffer2))
128 #define THREAD_SAFE_CALLBACKS(avctx) \
129 ((avctx)->thread_safe_callbacks || (avctx)->get_buffer2 == avcodec_default_get_buffer2)
133 * Codec worker thread.
135 * Automatically calls ff_thread_finish_setup() if the codec does
136 * not provide an update_thread_context method, or if the codec returns
139 static attribute_align_arg
void *frame_worker_thread(void *arg
)
141 PerThreadContext
*p
= arg
;
142 FrameThreadContext
*fctx
= p
->parent
;
143 AVCodecContext
*avctx
= p
->avctx
;
144 const AVCodec
*codec
= avctx
->codec
;
146 pthread_mutex_lock(&p
->mutex
);
148 while (p
->state
== STATE_INPUT_READY
&& !fctx
->die
)
149 pthread_cond_wait(&p
->input_cond
, &p
->mutex
);
151 if (fctx
->die
) break;
153 if (!codec
->update_thread_context
&& THREAD_SAFE_CALLBACKS(avctx
))
154 ff_thread_finish_setup(avctx
);
156 av_frame_unref(p
->frame
);
158 p
->result
= codec
->decode(avctx
, p
->frame
, &p
->got_frame
, &p
->avpkt
);
160 if ((p
->result
< 0 || !p
->got_frame
) && p
->frame
->buf
[0]) {
161 if (avctx
->internal
->allocate_progress
)
162 av_log(avctx
, AV_LOG_ERROR
, "A frame threaded decoder did not "
163 "free the frame on failure. This is a bug, please report it.\n");
164 av_frame_unref(p
->frame
);
167 if (p
->state
== STATE_SETTING_UP
) ff_thread_finish_setup(avctx
);
169 pthread_mutex_lock(&p
->progress_mutex
);
171 for (i
= 0; i
< MAX_BUFFERS
; i
++)
172 if (p
->progress_used
[i
] && (p
->got_frame
|| p
->result
<0 || avctx
->codec_id
!= AV_CODEC_ID_H264
)) {
173 p
->progress
[i
][0] = INT_MAX
;
174 p
->progress
[i
][1] = INT_MAX
;
177 p
->state
= STATE_INPUT_READY
;
179 pthread_cond_broadcast(&p
->progress_cond
);
180 pthread_cond_signal(&p
->output_cond
);
181 pthread_mutex_unlock(&p
->progress_mutex
);
183 pthread_mutex_unlock(&p
->mutex
);
189 * Update the next thread's AVCodecContext with values from the reference thread's context.
191 * @param dst The destination context.
192 * @param src The source context.
193 * @param for_user 0 if the destination is a codec thread, 1 if the destination is the user's thread
195 static int update_context_from_thread(AVCodecContext
*dst
, AVCodecContext
*src
, int for_user
)
200 dst
->time_base
= src
->time_base
;
201 dst
->framerate
= src
->framerate
;
202 dst
->width
= src
->width
;
203 dst
->height
= src
->height
;
204 dst
->pix_fmt
= src
->pix_fmt
;
206 dst
->coded_width
= src
->coded_width
;
207 dst
->coded_height
= src
->coded_height
;
209 dst
->has_b_frames
= src
->has_b_frames
;
210 dst
->idct_algo
= src
->idct_algo
;
212 dst
->bits_per_coded_sample
= src
->bits_per_coded_sample
;
213 dst
->sample_aspect_ratio
= src
->sample_aspect_ratio
;
215 FF_DISABLE_DEPRECATION_WARNINGS
216 dst
->dtg_active_format
= src
->dtg_active_format
;
217 FF_ENABLE_DEPRECATION_WARNINGS
218 #endif /* FF_API_AFD */
220 dst
->profile
= src
->profile
;
221 dst
->level
= src
->level
;
223 dst
->bits_per_raw_sample
= src
->bits_per_raw_sample
;
224 dst
->ticks_per_frame
= src
->ticks_per_frame
;
225 dst
->color_primaries
= src
->color_primaries
;
227 dst
->color_trc
= src
->color_trc
;
228 dst
->colorspace
= src
->colorspace
;
229 dst
->color_range
= src
->color_range
;
230 dst
->chroma_sample_location
= src
->chroma_sample_location
;
232 dst
->hwaccel
= src
->hwaccel
;
233 dst
->hwaccel_context
= src
->hwaccel_context
;
235 dst
->channels
= src
->channels
;
236 dst
->sample_rate
= src
->sample_rate
;
237 dst
->sample_fmt
= src
->sample_fmt
;
238 dst
->channel_layout
= src
->channel_layout
;
239 dst
->internal
->hwaccel_priv_data
= src
->internal
->hwaccel_priv_data
;
243 dst
->delay
= src
->thread_count
- 1;
244 dst
->coded_frame
= src
->coded_frame
;
246 if (dst
->codec
->update_thread_context
)
247 err
= dst
->codec
->update_thread_context(dst
, src
);
254 * Update the next thread's AVCodecContext with values set by the user.
256 * @param dst The destination context.
257 * @param src The source context.
258 * @return 0 on success, negative error code on failure
260 static int update_context_from_user(AVCodecContext
*dst
, AVCodecContext
*src
)
262 #define copy_fields(s, e) memcpy(&dst->s, &src->s, (char*)&dst->e - (char*)&dst->s);
263 dst
->flags
= src
->flags
;
265 dst
->draw_horiz_band
= src
->draw_horiz_band
;
266 dst
->get_buffer2
= src
->get_buffer2
;
267 #if FF_API_GET_BUFFER
268 FF_DISABLE_DEPRECATION_WARNINGS
269 dst
->get_buffer
= src
->get_buffer
;
270 dst
->release_buffer
= src
->release_buffer
;
271 FF_ENABLE_DEPRECATION_WARNINGS
274 dst
->opaque
= src
->opaque
;
275 dst
->debug
= src
->debug
;
276 dst
->debug_mv
= src
->debug_mv
;
278 dst
->slice_flags
= src
->slice_flags
;
279 dst
->flags2
= src
->flags2
;
281 copy_fields(skip_loop_filter
, subtitle_header
);
283 dst
->frame_number
= src
->frame_number
;
284 dst
->reordered_opaque
= src
->reordered_opaque
;
285 dst
->thread_safe_callbacks
= src
->thread_safe_callbacks
;
287 if (src
->slice_count
&& src
->slice_offset
) {
288 if (dst
->slice_count
< src
->slice_count
) {
289 int err
= av_reallocp_array(&dst
->slice_offset
, src
->slice_count
,
290 sizeof(*dst
->slice_offset
));
294 memcpy(dst
->slice_offset
, src
->slice_offset
,
295 src
->slice_count
* sizeof(*dst
->slice_offset
));
297 dst
->slice_count
= src
->slice_count
;
302 /// Releases the buffers that this decoding thread was the last user of.
303 static void release_delayed_buffers(PerThreadContext
*p
)
305 FrameThreadContext
*fctx
= p
->parent
;
307 while (p
->num_released_buffers
> 0) {
310 pthread_mutex_lock(&fctx
->buffer_mutex
);
312 // fix extended data in case the caller screwed it up
313 av_assert0(p
->avctx
->codec_type
== AVMEDIA_TYPE_VIDEO
||
314 p
->avctx
->codec_type
== AVMEDIA_TYPE_AUDIO
);
315 f
= &p
->released_buffers
[--p
->num_released_buffers
];
316 f
->extended_data
= f
->data
;
319 pthread_mutex_unlock(&fctx
->buffer_mutex
);
323 static int submit_packet(PerThreadContext
*p
, AVPacket
*avpkt
)
325 FrameThreadContext
*fctx
= p
->parent
;
326 PerThreadContext
*prev_thread
= fctx
->prev_thread
;
327 const AVCodec
*codec
= p
->avctx
->codec
;
329 if (!avpkt
->size
&& !(codec
->capabilities
& CODEC_CAP_DELAY
)) return 0;
331 pthread_mutex_lock(&p
->mutex
);
333 release_delayed_buffers(p
);
337 if (prev_thread
->state
== STATE_SETTING_UP
) {
338 pthread_mutex_lock(&prev_thread
->progress_mutex
);
339 while (prev_thread
->state
== STATE_SETTING_UP
)
340 pthread_cond_wait(&prev_thread
->progress_cond
, &prev_thread
->progress_mutex
);
341 pthread_mutex_unlock(&prev_thread
->progress_mutex
);
344 err
= update_context_from_thread(p
->avctx
, prev_thread
->avctx
, 0);
346 pthread_mutex_unlock(&p
->mutex
);
351 av_packet_unref(&p
->avpkt
);
352 av_packet_ref(&p
->avpkt
, avpkt
);
354 p
->state
= STATE_SETTING_UP
;
355 pthread_cond_signal(&p
->input_cond
);
356 pthread_mutex_unlock(&p
->mutex
);
359 * If the client doesn't have a thread-safe get_buffer(),
360 * then decoding threads call back to the main thread,
361 * and it calls back to the client here.
364 FF_DISABLE_DEPRECATION_WARNINGS
365 if (!p
->avctx
->thread_safe_callbacks
&& (
366 p
->avctx
->get_format
!= avcodec_default_get_format
||
367 #if FF_API_GET_BUFFER
368 p
->avctx
->get_buffer
||
370 p
->avctx
->get_buffer2
!= avcodec_default_get_buffer2
)) {
371 FF_ENABLE_DEPRECATION_WARNINGS
372 while (p
->state
!= STATE_SETUP_FINISHED
&& p
->state
!= STATE_INPUT_READY
) {
374 pthread_mutex_lock(&p
->progress_mutex
);
375 while (p
->state
== STATE_SETTING_UP
)
376 pthread_cond_wait(&p
->progress_cond
, &p
->progress_mutex
);
379 case STATE_GET_BUFFER
:
380 p
->result
= ff_get_buffer(p
->avctx
, p
->requested_frame
, p
->requested_flags
);
382 case STATE_GET_FORMAT
:
383 p
->result_format
= ff_get_format(p
->avctx
, p
->available_formats
);
390 p
->state
= STATE_SETTING_UP
;
391 pthread_cond_signal(&p
->progress_cond
);
393 pthread_mutex_unlock(&p
->progress_mutex
);
397 fctx
->prev_thread
= p
;
398 fctx
->next_decoding
++;
403 int ff_thread_decode_frame(AVCodecContext
*avctx
,
404 AVFrame
*picture
, int *got_picture_ptr
,
407 FrameThreadContext
*fctx
= avctx
->internal
->thread_ctx
;
408 int finished
= fctx
->next_finished
;
413 * Submit a packet to the next decoding thread.
416 p
= &fctx
->threads
[fctx
->next_decoding
];
417 err
= update_context_from_user(p
->avctx
, avctx
);
419 err
= submit_packet(p
, avpkt
);
423 * If we're still receiving the initial packets, don't return a frame.
426 if (fctx
->next_decoding
> (avctx
->thread_count
-1-(avctx
->codec_id
== AV_CODEC_ID_FFV1
)))
429 if (fctx
->delaying
) {
436 * Return the next available frame from the oldest thread.
437 * If we're at the end of the stream, then we have to skip threads that
438 * didn't output a frame, because we don't want to accidentally signal
439 * EOF (avpkt->size == 0 && *got_picture_ptr == 0).
443 p
= &fctx
->threads
[finished
++];
445 if (p
->state
!= STATE_INPUT_READY
) {
446 pthread_mutex_lock(&p
->progress_mutex
);
447 while (p
->state
!= STATE_INPUT_READY
)
448 pthread_cond_wait(&p
->output_cond
, &p
->progress_mutex
);
449 pthread_mutex_unlock(&p
->progress_mutex
);
452 av_frame_move_ref(picture
, p
->frame
);
453 *got_picture_ptr
= p
->got_frame
;
454 picture
->pkt_dts
= p
->avpkt
.dts
;
457 * A later call with avkpt->size == 0 may loop over all threads,
458 * including this one, searching for a frame to return before being
459 * stopped by the "finished != fctx->next_finished" condition.
460 * Make sure we don't mistakenly return the same frame again.
464 if (finished
>= avctx
->thread_count
) finished
= 0;
465 } while (!avpkt
->size
&& !*got_picture_ptr
&& finished
!= fctx
->next_finished
);
467 update_context_from_thread(avctx
, p
->avctx
, 1);
469 if (fctx
->next_decoding
>= avctx
->thread_count
) fctx
->next_decoding
= 0;
471 fctx
->next_finished
= finished
;
473 /* return the size of the consumed packet if no error occurred */
474 return (p
->result
>= 0) ? avpkt
->size
: p
->result
;
477 void ff_thread_report_progress(ThreadFrame
*f
, int n
, int field
)
480 volatile int *progress
= f
->progress
? (int*)f
->progress
->data
: NULL
;
482 if (!progress
|| progress
[field
] >= n
) return;
484 p
= f
->owner
->internal
->thread_ctx
;
486 if (f
->owner
->debug
&FF_DEBUG_THREADS
)
487 av_log(f
->owner
, AV_LOG_DEBUG
, "%p finished %d field %d\n", progress
, n
, field
);
489 pthread_mutex_lock(&p
->progress_mutex
);
491 pthread_cond_broadcast(&p
->progress_cond
);
492 pthread_mutex_unlock(&p
->progress_mutex
);
495 void ff_thread_await_progress(ThreadFrame
*f
, int n
, int field
)
498 volatile int *progress
= f
->progress
? (int*)f
->progress
->data
: NULL
;
500 if (!progress
|| progress
[field
] >= n
) return;
502 p
= f
->owner
->internal
->thread_ctx
;
504 if (f
->owner
->debug
&FF_DEBUG_THREADS
)
505 av_log(f
->owner
, AV_LOG_DEBUG
, "thread awaiting %d field %d from %p\n", n
, field
, progress
);
507 pthread_mutex_lock(&p
->progress_mutex
);
508 while (progress
[field
] < n
)
509 pthread_cond_wait(&p
->progress_cond
, &p
->progress_mutex
);
510 pthread_mutex_unlock(&p
->progress_mutex
);
513 void ff_thread_finish_setup(AVCodecContext
*avctx
) {
514 PerThreadContext
*p
= avctx
->internal
->thread_ctx
;
516 if (!(avctx
->active_thread_type
&FF_THREAD_FRAME
)) return;
518 if(p
->state
== STATE_SETUP_FINISHED
){
519 av_log(avctx
, AV_LOG_WARNING
, "Multiple ff_thread_finish_setup() calls\n");
522 pthread_mutex_lock(&p
->progress_mutex
);
523 p
->state
= STATE_SETUP_FINISHED
;
524 pthread_cond_broadcast(&p
->progress_cond
);
525 pthread_mutex_unlock(&p
->progress_mutex
);
528 /// Waits for all threads to finish.
529 static void park_frame_worker_threads(FrameThreadContext
*fctx
, int thread_count
)
533 for (i
= 0; i
< thread_count
; i
++) {
534 PerThreadContext
*p
= &fctx
->threads
[i
];
536 if (p
->state
!= STATE_INPUT_READY
) {
537 pthread_mutex_lock(&p
->progress_mutex
);
538 while (p
->state
!= STATE_INPUT_READY
)
539 pthread_cond_wait(&p
->output_cond
, &p
->progress_mutex
);
540 pthread_mutex_unlock(&p
->progress_mutex
);
546 void ff_frame_thread_free(AVCodecContext
*avctx
, int thread_count
)
548 FrameThreadContext
*fctx
= avctx
->internal
->thread_ctx
;
549 const AVCodec
*codec
= avctx
->codec
;
552 park_frame_worker_threads(fctx
, thread_count
);
554 if (fctx
->prev_thread
&& fctx
->prev_thread
!= fctx
->threads
)
555 if (update_context_from_thread(fctx
->threads
->avctx
, fctx
->prev_thread
->avctx
, 0) < 0) {
556 av_log(avctx
, AV_LOG_ERROR
, "Final thread update failed\n");
557 fctx
->prev_thread
->avctx
->internal
->is_copy
= fctx
->threads
->avctx
->internal
->is_copy
;
558 fctx
->threads
->avctx
->internal
->is_copy
= 1;
563 for (i
= 0; i
< thread_count
; i
++) {
564 PerThreadContext
*p
= &fctx
->threads
[i
];
566 pthread_mutex_lock(&p
->mutex
);
567 pthread_cond_signal(&p
->input_cond
);
568 pthread_mutex_unlock(&p
->mutex
);
571 pthread_join(p
->thread
, NULL
);
575 codec
->close(p
->avctx
);
579 release_delayed_buffers(p
);
580 av_frame_free(&p
->frame
);
583 for (i
= 0; i
< thread_count
; i
++) {
584 PerThreadContext
*p
= &fctx
->threads
[i
];
586 pthread_mutex_destroy(&p
->mutex
);
587 pthread_mutex_destroy(&p
->progress_mutex
);
588 pthread_cond_destroy(&p
->input_cond
);
589 pthread_cond_destroy(&p
->progress_cond
);
590 pthread_cond_destroy(&p
->output_cond
);
591 av_packet_unref(&p
->avpkt
);
592 av_freep(&p
->released_buffers
);
595 av_freep(&p
->avctx
->priv_data
);
596 av_freep(&p
->avctx
->slice_offset
);
599 av_freep(&p
->avctx
->internal
);
603 av_freep(&fctx
->threads
);
604 pthread_mutex_destroy(&fctx
->buffer_mutex
);
605 av_freep(&avctx
->internal
->thread_ctx
);
608 int ff_frame_thread_init(AVCodecContext
*avctx
)
610 int thread_count
= avctx
->thread_count
;
611 const AVCodec
*codec
= avctx
->codec
;
612 AVCodecContext
*src
= avctx
;
613 FrameThreadContext
*fctx
;
621 int nb_cpus
= av_cpu_count();
622 if ((avctx
->debug
& (FF_DEBUG_VIS_QP
| FF_DEBUG_VIS_MB_TYPE
)) || avctx
->debug_mv
)
624 // use number of cores + 1 as thread count if there is more than one
626 thread_count
= avctx
->thread_count
= FFMIN(nb_cpus
+ 1, MAX_AUTO_THREADS
);
628 thread_count
= avctx
->thread_count
= 1;
631 if (thread_count
<= 1) {
632 avctx
->active_thread_type
= 0;
636 avctx
->internal
->thread_ctx
= fctx
= av_mallocz(sizeof(FrameThreadContext
));
638 fctx
->threads
= av_mallocz_array(thread_count
, sizeof(PerThreadContext
));
639 pthread_mutex_init(&fctx
->buffer_mutex
, NULL
);
642 for (i
= 0; i
< thread_count
; i
++) {
643 AVCodecContext
*copy
= av_malloc(sizeof(AVCodecContext
));
644 PerThreadContext
*p
= &fctx
->threads
[i
];
646 pthread_mutex_init(&p
->mutex
, NULL
);
647 pthread_mutex_init(&p
->progress_mutex
, NULL
);
648 pthread_cond_init(&p
->input_cond
, NULL
);
649 pthread_cond_init(&p
->progress_cond
, NULL
);
650 pthread_cond_init(&p
->output_cond
, NULL
);
652 p
->frame
= av_frame_alloc();
655 err
= AVERROR(ENOMEM
);
663 err
= AVERROR(ENOMEM
);
669 copy
->internal
= av_malloc(sizeof(AVCodecInternal
));
670 if (!copy
->internal
) {
671 err
= AVERROR(ENOMEM
);
674 *copy
->internal
= *src
->internal
;
675 copy
->internal
->thread_ctx
= p
;
676 copy
->internal
->pkt
= &p
->avpkt
;
682 err
= codec
->init(copy
);
684 update_context_from_thread(avctx
, copy
, 1);
686 copy
->priv_data
= av_malloc(codec
->priv_data_size
);
687 if (!copy
->priv_data
) {
688 err
= AVERROR(ENOMEM
);
691 memcpy(copy
->priv_data
, src
->priv_data
, codec
->priv_data_size
);
692 copy
->internal
->is_copy
= 1;
694 if (codec
->init_thread_copy
)
695 err
= codec
->init_thread_copy(copy
);
700 err
= AVERROR(pthread_create(&p
->thread
, NULL
, frame_worker_thread
, p
));
701 p
->thread_init
= !err
;
709 ff_frame_thread_free(avctx
, i
+1);
714 void ff_thread_flush(AVCodecContext
*avctx
)
717 FrameThreadContext
*fctx
= avctx
->internal
->thread_ctx
;
721 park_frame_worker_threads(fctx
, avctx
->thread_count
);
722 if (fctx
->prev_thread
) {
723 if (fctx
->prev_thread
!= &fctx
->threads
[0])
724 update_context_from_thread(fctx
->threads
[0].avctx
, fctx
->prev_thread
->avctx
, 0);
727 fctx
->next_decoding
= fctx
->next_finished
= 0;
729 fctx
->prev_thread
= NULL
;
730 for (i
= 0; i
< avctx
->thread_count
; i
++) {
731 PerThreadContext
*p
= &fctx
->threads
[i
];
732 // Make sure decode flush calls with size=0 won't return old frames
734 av_frame_unref(p
->frame
);
736 release_delayed_buffers(p
);
738 if (avctx
->codec
->flush
)
739 avctx
->codec
->flush(p
->avctx
);
743 int ff_thread_can_start_frame(AVCodecContext
*avctx
)
745 PerThreadContext
*p
= avctx
->internal
->thread_ctx
;
746 if ((avctx
->active_thread_type
&FF_THREAD_FRAME
) && p
->state
!= STATE_SETTING_UP
&&
747 (avctx
->codec
->update_thread_context
|| !THREAD_SAFE_CALLBACKS(avctx
))) {
753 static int thread_get_buffer_internal(AVCodecContext
*avctx
, ThreadFrame
*f
, int flags
)
755 PerThreadContext
*p
= avctx
->internal
->thread_ctx
;
760 ff_init_buffer_info(avctx
, f
->f
);
762 if (!(avctx
->active_thread_type
& FF_THREAD_FRAME
))
763 return ff_get_buffer(avctx
, f
->f
, flags
);
765 if (p
->state
!= STATE_SETTING_UP
&&
766 (avctx
->codec
->update_thread_context
|| !THREAD_SAFE_CALLBACKS(avctx
))) {
767 av_log(avctx
, AV_LOG_ERROR
, "get_buffer() cannot be called after ff_thread_finish_setup()\n");
771 if (avctx
->internal
->allocate_progress
) {
773 f
->progress
= av_buffer_alloc(2 * sizeof(int));
775 return AVERROR(ENOMEM
);
777 progress
= (int*)f
->progress
->data
;
779 progress
[0] = progress
[1] = -1;
782 pthread_mutex_lock(&p
->parent
->buffer_mutex
);
783 FF_DISABLE_DEPRECATION_WARNINGS
784 if (avctx
->thread_safe_callbacks
|| (
785 #if FF_API_GET_BUFFER
786 !avctx
->get_buffer
&&
788 avctx
->get_buffer2
== avcodec_default_get_buffer2
)) {
789 FF_ENABLE_DEPRECATION_WARNINGS
790 err
= ff_get_buffer(avctx
, f
->f
, flags
);
792 pthread_mutex_lock(&p
->progress_mutex
);
793 p
->requested_frame
= f
->f
;
794 p
->requested_flags
= flags
;
795 p
->state
= STATE_GET_BUFFER
;
796 pthread_cond_broadcast(&p
->progress_cond
);
798 while (p
->state
!= STATE_SETTING_UP
)
799 pthread_cond_wait(&p
->progress_cond
, &p
->progress_mutex
);
803 pthread_mutex_unlock(&p
->progress_mutex
);
806 if (!THREAD_SAFE_CALLBACKS(avctx
) && !avctx
->codec
->update_thread_context
)
807 ff_thread_finish_setup(avctx
);
810 av_buffer_unref(&f
->progress
);
812 pthread_mutex_unlock(&p
->parent
->buffer_mutex
);
817 enum AVPixelFormat
ff_thread_get_format(AVCodecContext
*avctx
, const enum AVPixelFormat
*fmt
)
819 enum AVPixelFormat res
;
820 PerThreadContext
*p
= avctx
->internal
->thread_ctx
;
821 if (!(avctx
->active_thread_type
& FF_THREAD_FRAME
) || avctx
->thread_safe_callbacks
||
822 avctx
->get_format
== avcodec_default_get_format
)
823 return ff_get_format(avctx
, fmt
);
824 if (p
->state
!= STATE_SETTING_UP
) {
825 av_log(avctx
, AV_LOG_ERROR
, "get_format() cannot be called after ff_thread_finish_setup()\n");
828 pthread_mutex_lock(&p
->progress_mutex
);
829 p
->available_formats
= fmt
;
830 p
->state
= STATE_GET_FORMAT
;
831 pthread_cond_broadcast(&p
->progress_cond
);
833 while (p
->state
!= STATE_SETTING_UP
)
834 pthread_cond_wait(&p
->progress_cond
, &p
->progress_mutex
);
836 res
= p
->result_format
;
838 pthread_mutex_unlock(&p
->progress_mutex
);
843 int ff_thread_get_buffer(AVCodecContext
*avctx
, ThreadFrame
*f
, int flags
)
845 int ret
= thread_get_buffer_internal(avctx
, f
, flags
);
847 av_log(avctx
, AV_LOG_ERROR
, "thread_get_buffer() failed\n");
851 void ff_thread_release_buffer(AVCodecContext
*avctx
, ThreadFrame
*f
)
853 PerThreadContext
*p
= avctx
->internal
->thread_ctx
;
854 FrameThreadContext
*fctx
;
856 FF_DISABLE_DEPRECATION_WARNINGS
857 int can_direct_free
= !(avctx
->active_thread_type
& FF_THREAD_FRAME
) ||
858 avctx
->thread_safe_callbacks
||
860 #if FF_API_GET_BUFFER
861 !avctx
->get_buffer
&&
863 avctx
->get_buffer2
== avcodec_default_get_buffer2
);
864 FF_ENABLE_DEPRECATION_WARNINGS
866 if (!f
->f
|| !f
->f
->buf
[0])
869 if (avctx
->debug
& FF_DEBUG_BUFFERS
)
870 av_log(avctx
, AV_LOG_DEBUG
, "thread_release_buffer called on pic %p\n", f
);
872 av_buffer_unref(&f
->progress
);
875 if (can_direct_free
) {
876 av_frame_unref(f
->f
);
881 pthread_mutex_lock(&fctx
->buffer_mutex
);
883 if (p
->num_released_buffers
+ 1 >= INT_MAX
/ sizeof(*p
->released_buffers
))
885 tmp
= av_fast_realloc(p
->released_buffers
, &p
->released_buffers_allocated
,
886 (p
->num_released_buffers
+ 1) *
887 sizeof(*p
->released_buffers
));
890 p
->released_buffers
= tmp
;
892 dst
= &p
->released_buffers
[p
->num_released_buffers
];
893 av_frame_move_ref(dst
, f
->f
);
895 p
->num_released_buffers
++;
898 pthread_mutex_unlock(&fctx
->buffer_mutex
);