X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=modules%2Fffmpeg%2Fproducer%2Ffilter%2Fparallel_yadif.cpp;h=1727a4ce84a3c9c7ff2660c803467c9aa5dbbcfc;hb=1b54cebcda72c294c6e112a30c2b353b8489048b;hp=4b2483ba95bd06bd5a70c3d3281c8dea9c568cc9;hpb=8a8695aa1ba59ef018d478c52c38c94d2b03a0f1;p=casparcg diff --git a/modules/ffmpeg/producer/filter/parallel_yadif.cpp b/modules/ffmpeg/producer/filter/parallel_yadif.cpp index 4b2483ba9..1727a4ce8 100644 --- a/modules/ffmpeg/producer/filter/parallel_yadif.cpp +++ b/modules/ffmpeg/producer/filter/parallel_yadif.cpp @@ -2,10 +2,22 @@ #include "parallel_yadif.h" +#include + +#if defined(_MSC_VER) +#pragma warning (push) +#pragma warning (disable : 4244) +#endif extern "C" { #include } +#if defined(_MSC_VER) +#pragma warning (pop) +#endif + +#include +#include #include @@ -39,8 +51,9 @@ struct parallel_yadif_context int mode; }; - arg args[64]; + arg args[1080]; int index; + int last_index; parallel_yadif_context() : index(0){} }; @@ -52,7 +65,7 @@ void parallel_yadif_filter_line(parallel_yadif_context& ctx, uint8_t *dst, uint8 parallel_yadif_context::arg arg = {dst, prev, cur, next, w, prefs, mrefs, parity, mode}; ctx.args[ctx.index++] = arg; - if(ctx.index == 64) + if(ctx.index == ctx.last_index) { tbb::parallel_for(tbb::blocked_range(0, ctx.index), [=](const tbb::blocked_range& r) { @@ -63,54 +76,59 @@ void parallel_yadif_filter_line(parallel_yadif_context& ctx, uint8_t *dst, uint8 } } +namespace caspar { + +tbb::concurrent_bounded_queue parallel_line_func_pool; +std::array ctxs; + #define RENAME(a) f ## a #define ff(x) \ void RENAME(x)(uint8_t *dst, uint8_t *prev, uint8_t *cur, uint8_t *next, int w, int prefs, int mrefs, int parity, int mode) \ {\ - static parallel_yadif_context ctx;\ - parallel_yadif_filter_line(ctx, dst, prev, cur, next, w, prefs, mrefs, parity, mode);\ + parallel_yadif_filter_line(ctxs[x], dst, prev, cur, next, w, prefs, mrefs, parity, mode);\ } ff(0); ff(1); ff(2); ff(3); ff(4); ff(5); ff(6); ff(7); ff(8); ff(9); ff(10); ff(11); ff(12); ff(13); ff(14); ff(15); ff(16); ff(17); void (*fs[])(uint8_t *dst, uint8_t *prev, uint8_t *cur, uint8_t *next, int w, int prefs, int mrefs, int parity, int mode) = - {f0, f1, f2, f3, f4, f5, f6, f7, f8, f9, f10, f11, f12, f13, f14, f15, f16, f17}; -namespace caspar { - -tbb::concurrent_bounded_queue tags; void init_pool() { - for(int n = 0; n < 18; ++n) - tags.push(n); + for(int n = 0; n < sizeof(fs)/sizeof(fs[0]); ++n) + parallel_line_func_pool.push(fs[n]); } -int init(AVFilterContext* ctx) +void return_parallel_yadif(void* func) +{ + if(func != nullptr) + parallel_line_func_pool.push(reinterpret_cast(func)); +} + +std::shared_ptr make_parallel_yadif(AVFilterContext* ctx) { static boost::once_flag flag = BOOST_ONCE_INIT; boost::call_once(&init_pool, flag); YADIFContext* yadif = (YADIFContext*)ctx->priv; org_yadif_filter_line = yadif->filter_line; // Data race is not a problem. - - int tag; - if(!tags.try_pop(tag)) + + decltype(org_yadif_filter_line) func = nullptr; + if(!parallel_line_func_pool.try_pop(func)) + CASPAR_LOG(warning) << "Not enough scalable-yadif context instances. Running non-scalable"; + else { - CASPAR_LOG(warning) << "Not enough scalable-yadif instances. Running non-scalable"; - return -1; - } + int index = 0; + while(index < sizeof(fs)/sizeof(fs[0]) && fs[index] != func) + ++index; - yadif->filter_line = fs[tag]; - return tag; -} + ctxs[index].last_index = 32;//ctx->inputs[0]->h; + yadif->filter_line = func; + } -void uninit(int tag) -{ - if(tag != -1) - tags.push(tag); + return std::shared_ptr(func, return_parallel_yadif); } } \ No newline at end of file