Skip to content
divVerent edited this page Sep 10, 2012 · 38 revisions

Using the video from http://mirror.bigbuckbunny.de/peach/bigbuckbunny_movies/big_buck_bunny_1080p_stereo.ogg (shortened mirror: http://ompldr.org/vZmZmeQ/big_buck_bunny_1080p_stereo-61s.ogg):

F=big_buck_bunny_1080p_stereo.ogg
D=60
test_f_1()
{
  /usr/bin/time -p mplayer "$F" -endpos "$D" -quiet -untimed -no-audio -vo null "$@" 2>&1 >/dev/null | tail -n 3 | head -n 1 | cut -d ' ' -f 2
}
test_f()
{
  f=$1
  echo -n "$f: "
  shift
  case "$f" in
    geq) test_f_1 "$@" ;;
    *)   a=; for t in 1 2 3 4 5; do r=`test_f_1 "$@"`; echo -n "$r "; a="$a $r"; done; echo -n "-> "; echo "$a" | xargs -n 1 echo | sort -n | head -n 3 | tail -n 1 ;;
  esac
}
test_f "No filter"
test_f "eq2"       -vf eq2=1:-1
test_f "lua-pxy"   -vf lua=fn_l='1-p(x\,y)'
test_f "lua-c"     -vf lua=fn_l='1-c'
test_f "lua-lut"   -vf lua=lut_l='1-c'
test_f "dlopen"    -vf dlopen=./invert_y.so
test_f "geq"       -vf geq='255-p(X\,Y)':'p(X\,Y)':'p(X\,Y)'

Results (by divVerent, running LuaJIT 2.0.0-beta10 on AMD Athlon(tm) II X4 620 Processor @ 2.6GHz):

No filter: 7.19 7.11 7.10 7.11 7.11 -> 7.11
eq2: 7.68 7.72 7.84 8.09 7.87 -> 7.84
lua-pxy: 40.93 40.92 40.91 40.90 40.92 -> 40.92
dlopen: 7.98 8.02 7.98 7.98 7.98 -> 7.98
geq: 333.80

Results (by wm4, running LuaJIT 2.0.0-beta9 on Intel(R) Core(TM)2 Duo CPU E6550 @ 2.33GHz):

No filter: 14.32 14.44 14.54 14.43 14.51 -> 14.44
eq2: 15.24 15.29 15.21 15.24 15.27 -> 15.24
lua-pxy: 23.04 23.10 23.14 23.30 22.93 -> 23.10
dlopen: 16.44 16.30 16.24 16.20 16.03 -> 16.24
geq: 555.20

invert_y.c:

#include <assert.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include "vf_dlopen.h"
#include "filterutils.h"

/*
 * luma inverter
 *
 * usage: -vf dlopen=./invert_y.so
 *
 * inverts the luma plane. Duh.
 */

static void invert_plane(
    unsigned char *dest, unsigned dest_stride,
    const unsigned char *src, unsigned src_stride,
    unsigned length,
    unsigned rows
    )
{
    unsigned i, j;
    assert(dest_stride >= length);
    assert(src_stride >= length);
    for (i = 0; i < rows; ++i)
    {
        const unsigned char *s = &src[src_stride * i];
        unsigned char *d = &dest[dest_stride * i];
        for (j = 0; j < length; ++j)
            *d++ = *s++ ^ 0xFF;
    }
}

static int iy_put_image(struct vf_dlopen_context *ctx)
{
    unsigned int p;

    assert(ctx->inpic.planes == ctx->outpic->planes);

    for (p = 0; p < ctx->outpic->planes; ++p) {
        assert(ctx->inpic.planewidth[p] == ctx->outpic->planewidth[p]);
        assert(ctx->inpic.planeheight[p] == ctx->outpic->planeheight[p]);
    }

    invert_plane(
            ctx->outpic->plane[0], ctx->outpic->planestride[0],
            ctx->inpic.plane[0], ctx->inpic.planestride[0],
            ctx->inpic.planewidth[0], ctx->inpic.planeheight[0]
        );
    for (p = 1; p < ctx->outpic->planes; ++p) {
        copy_plane(
                ctx->outpic->plane[p], ctx->outpic->planestride[p],
                ctx->inpic.plane[p], ctx->inpic.planestride[p],
                ctx->inpic.planewidth[p], ctx->inpic.planeheight[p]
            );
    }

    ctx->outpic->pts = ctx->inpic.pts;
    return 1;
}

int vf_dlopen_getcontext(struct vf_dlopen_context *ctx, int argc, const char **argv)
{
    VF_DLOPEN_CHECK_VERSION(ctx);
    (void) argc;
    (void) argv;
    static struct vf_dlopen_formatpair map[] = {
        { "yv12", "yv12" },
        { NULL, NULL }
    };
    ctx->format_mapping = map;
    ctx->put_image = iy_put_image;
    return 1;
}

To compile this filter, put it in TOOLS/vf_dlopen/invert_y.c and edit the Makefile so that FILTERS includes invert_y, then run make.

Clone this wiki locally