diff --git a/media/ffvpx/README_MOZILLA b/media/ffvpx/README_MOZILLA index 050c849d79ac..ae62c383958d 100644 --- a/media/ffvpx/README_MOZILLA +++ b/media/ffvpx/README_MOZILLA @@ -30,3 +30,10 @@ replace: s/HAVE_SYSCTL 1/HAVE_SYSCTL 0 config_win32/64.h/asm: add to configure command: --toolchain=msvc + +23 Sept 2016: libavcodec/pthread_frame.c has been patched so as to avoid +generating large numbers of warnings from TSan (Thread Sanitizer) when +decoding vp9 streams. This will likely be fixed upstream sometime soon. +When resyncing with upstream, first un-apply the patch shown at +https://bugzilla.mozilla.org/show_bug.cgi?id=1274256#c60, then resync, +then assess whether the patch is still necessary. diff --git a/media/ffvpx/libavcodec/pthread_frame.c b/media/ffvpx/libavcodec/pthread_frame.c index 7ef5e9f6be92..a10fcbfe714d 100644 --- a/media/ffvpx/libavcodec/pthread_frame.c +++ b/media/ffvpx/libavcodec/pthread_frame.c @@ -43,9 +43,29 @@ #include "libavutil/opt.h" #include "libavutil/thread.h" +#if defined(MOZ_TSAN) +typedef _Atomic(int) atomic_int; +#else +typedef volatile int atomic_int; +#endif + /** * Context used by codec threads and stored in their AVCodecInternal thread_ctx. */ +typedef enum { + STATE_INPUT_READY, ///< Set when the thread is awaiting a packet. + STATE_SETTING_UP, ///< Set before the codec has called ff_thread_finish_setup(). + STATE_GET_BUFFER, /**< + * Set when the codec calls get_buffer(). + * State is returned to STATE_SETTING_UP afterwards. + */ + STATE_GET_FORMAT, /**< + * Set when the codec calls get_format(). + * State is returned to STATE_SETTING_UP afterwards. + */ + STATE_SETUP_FINISHED ///< Set after the codec has called ff_thread_finish_setup(). +} State; + typedef struct PerThreadContext { struct FrameThreadContext *parent; @@ -66,19 +86,7 @@ typedef struct PerThreadContext { int got_frame; ///< The output of got_picture_ptr from the last avcodec_decode_video() call. int result; ///< The result of the last codec decode/encode() call. - enum { - STATE_INPUT_READY, ///< Set when the thread is awaiting a packet. - STATE_SETTING_UP, ///< Set before the codec has called ff_thread_finish_setup(). - STATE_GET_BUFFER, /**< - * Set when the codec calls get_buffer(). - * State is returned to STATE_SETTING_UP afterwards. - */ - STATE_GET_FORMAT, /**< - * Set when the codec calls get_format(). - * State is returned to STATE_SETTING_UP afterwards. - */ - STATE_SETUP_FINISHED ///< Set after the codec has called ff_thread_finish_setup(). - } state; + atomic_int state; /** * Array of frames passed to ff_thread_release_buffer(). @@ -358,7 +366,8 @@ static int submit_packet(PerThreadContext *p, AVPacket *avpkt) while (p->state == STATE_SETTING_UP) pthread_cond_wait(&p->progress_cond, &p->progress_mutex); - switch (p->state) { + State p_state = (State)p->state; + switch (p_state) { case STATE_GET_BUFFER: p->result = ff_get_buffer(p->avctx, p->requested_frame, p->requested_flags); break; @@ -471,7 +480,7 @@ int ff_thread_decode_frame(AVCodecContext *avctx, void ff_thread_report_progress(ThreadFrame *f, int n, int field) { PerThreadContext *p; - volatile int *progress = f->progress ? (int*)f->progress->data : NULL; + atomic_int *progress = f->progress ? (atomic_int*)f->progress->data : NULL; if (!progress || progress[field] >= n) return; @@ -489,7 +498,7 @@ void ff_thread_report_progress(ThreadFrame *f, int n, int field) void ff_thread_await_progress(ThreadFrame *f, int n, int field) { PerThreadContext *p; - volatile int *progress = f->progress ? (int*)f->progress->data : NULL; + atomic_int *progress = f->progress ? (atomic_int*)f->progress->data : NULL; if (!progress || progress[field] >= n) return;