Go to the documentation of this file.
92 #define GET_MODE_BUFFER_SIZE 500
93 #define OPTIONS_ARRAY_SIZE 10
98 #define DERING_THRESHOLD 20
100 #if ARCH_X86 && HAVE_INLINE_ASM
120 {
"dr",
"dering", 1, 5, 6,
DERING},
121 {
"al",
"autolevels", 0, 1, 2,
LEVEL_FIX},
130 {
"be",
"bitexact", 1, 0, 0,
BITEXACT},
137 "default",
"hb:a,vb:a,dr:a",
138 "de",
"hb:a,vb:a,dr:a",
139 "fast",
"h1:a,v1:a,dr:a",
140 "fa",
"h1:a,v1:a,dr:a",
141 "ac",
"ha:a:128:7,va:a,dr:a",
155 const int dcOffset= ((
c->nonBQP*
c->ppMode.baseDcDiff)>>8) + 1;
156 const int dcThreshold= dcOffset*2 + 1;
159 numEq += ((unsigned)(
src[0] -
src[1] + dcOffset)) < dcThreshold;
160 numEq += ((unsigned)(
src[1] -
src[2] + dcOffset)) < dcThreshold;
161 numEq += ((unsigned)(
src[2] -
src[3] + dcOffset)) < dcThreshold;
162 numEq += ((unsigned)(
src[3] -
src[4] + dcOffset)) < dcThreshold;
163 numEq += ((unsigned)(
src[4] -
src[5] + dcOffset)) < dcThreshold;
164 numEq += ((unsigned)(
src[5] -
src[6] + dcOffset)) < dcThreshold;
165 numEq += ((unsigned)(
src[6] -
src[7] + dcOffset)) < dcThreshold;
168 return numEq >
c->ppMode.flatnessThreshold;
178 const int dcOffset= ((
c->nonBQP*
c->ppMode.baseDcDiff)>>8) + 1;
179 const int dcThreshold= dcOffset*2 + 1;
183 numEq += ((unsigned)(
src[0] -
src[0+
stride] + dcOffset)) < dcThreshold;
184 numEq += ((unsigned)(
src[1] -
src[1+
stride] + dcOffset)) < dcThreshold;
185 numEq += ((unsigned)(
src[2] -
src[2+
stride] + dcOffset)) < dcThreshold;
186 numEq += ((unsigned)(
src[3] -
src[3+
stride] + dcOffset)) < dcThreshold;
187 numEq += ((unsigned)(
src[4] -
src[4+
stride] + dcOffset)) < dcThreshold;
188 numEq += ((unsigned)(
src[5] -
src[5+
stride] + dcOffset)) < dcThreshold;
189 numEq += ((unsigned)(
src[6] -
src[6+
stride] + dcOffset)) < dcThreshold;
190 numEq += ((unsigned)(
src[7] -
src[7+
stride] + dcOffset)) < dcThreshold;
193 return numEq >
c->ppMode.flatnessThreshold;
200 if((
unsigned)(
src[0] -
src[5] + 2*
QP) > 4*
QP)
return 0;
202 if((
unsigned)(
src[2] -
src[7] + 2*
QP) > 4*
QP)
return 0;
204 if((
unsigned)(
src[4] -
src[1] + 2*
QP) > 4*
QP)
return 0;
206 if((
unsigned)(
src[6] -
src[3] + 2*
QP) > 4*
QP)
return 0;
247 const int middleEnergy= 5*(
dst[4] -
dst[3]) + 2*(
dst[2] -
dst[5]);
249 if(
FFABS(middleEnergy) < 8*
c->QP){
250 const int q=(
dst[3] -
dst[4])/2;
251 const int leftEnergy= 5*(
dst[2] -
dst[1]) + 2*(
dst[0] -
dst[3]);
252 const int rightEnergy= 5*(
dst[6] -
dst[5]) + 2*(
dst[4] -
dst[7]);
258 d*=
FFSIGN(-middleEnergy);
295 sums[5] = sums[4] -
dst[0] +
dst[7];
296 sums[6] = sums[5] -
dst[1] + last;
297 sums[7] = sums[6] -
dst[2] + last;
298 sums[8] = sums[7] -
dst[3] + last;
299 sums[9] = sums[8] -
dst[4] + last;
301 dst[0]= (sums[0] + sums[2] + 2*
dst[0])>>4;
302 dst[1]= (sums[1] + sums[3] + 2*
dst[1])>>4;
303 dst[2]= (sums[2] + sums[4] + 2*
dst[2])>>4;
304 dst[3]= (sums[3] + sums[5] + 2*
dst[3])>>4;
305 dst[4]= (sums[4] + sums[6] + 2*
dst[4])>>4;
306 dst[5]= (sums[5] + sums[7] + 2*
dst[5])>>4;
307 dst[6]= (sums[6] + sums[8] + 2*
dst[6])>>4;
308 dst[7]= (sums[7] + sums[9] + 2*
dst[7])>>4;
325 static uint64_t lut[256];
331 int v=
i < 128 ? 2*
i : 2*(
i-256);
340 uint64_t
a= (v/16) & 0xFF;
341 uint64_t
b= (v*3/16) & 0xFF;
342 uint64_t
c= (v*5/16) & 0xFF;
343 uint64_t d= (7*v/16) & 0xFF;
344 uint64_t
A= (0x100 -
a)&0xFF;
345 uint64_t
B= (0x100 -
b)&0xFF;
346 uint64_t
C= (0x100 -
c)&0xFF;
347 uint64_t
D= (0x100 -
c)&0xFF;
349 lut[
i] = (
a<<56) | (
b<<48) | (
c<<40) | (d<<32) |
350 (
D<<24) | (
C<<16) | (
B<<8) | (
A);
384 const int dcOffset= ((
c->nonBQP*
c->ppMode.baseDcDiff)>>8) + 1;
385 const int dcThreshold= dcOffset*2 + 1;
391 numEq += ((unsigned)(
src[-1*
step] -
src[0*
step] + dcOffset)) < dcThreshold;
392 numEq += ((unsigned)(
src[ 0*
step] -
src[1*
step] + dcOffset)) < dcThreshold;
393 numEq += ((unsigned)(
src[ 1*
step] -
src[2*
step] + dcOffset)) < dcThreshold;
394 numEq += ((unsigned)(
src[ 2*
step] -
src[3*
step] + dcOffset)) < dcThreshold;
395 numEq += ((unsigned)(
src[ 3*
step] -
src[4*
step] + dcOffset)) < dcThreshold;
396 numEq += ((unsigned)(
src[ 4*
step] -
src[5*
step] + dcOffset)) < dcThreshold;
397 numEq += ((unsigned)(
src[ 5*
step] -
src[6*
step] + dcOffset)) < dcThreshold;
398 numEq += ((unsigned)(
src[ 6*
step] -
src[7*
step] + dcOffset)) < dcThreshold;
399 numEq += ((unsigned)(
src[ 7*
step] -
src[8*
step] + dcOffset)) < dcThreshold;
400 if(numEq >
c->ppMode.flatnessThreshold){
430 sums[6] = sums[5] -
src[1*
step] + last;
431 sums[7] = sums[6] -
src[2*
step] + last;
432 sums[8] = sums[7] -
src[3*
step] + last;
433 sums[9] = sums[8] -
src[4*
step] + last;
457 if(
FFABS(middleEnergy) < 8*
QP){
466 d*=
FFSIGN(-middleEnergy);
477 d= (d < 0) ? 32 : -32;
495 #define TEMPLATE_PP_C 1
501 # define TEMPLATE_PP_ALTIVEC 1
506 #if ARCH_X86 && HAVE_INLINE_ASM
507 # if CONFIG_RUNTIME_CPUDETECT
508 # define TEMPLATE_PP_SSE2 1
511 # if HAVE_SSE2_INLINE
512 # define TEMPLATE_PP_SSE2 1
519 const int8_t QPs[],
int QPStride,
int isColor,
PPContext *
c2);
524 pp_fn pp = postProcess_C;
530 #if CONFIG_RUNTIME_CPUDETECT
531 #if ARCH_X86 && HAVE_INLINE_ASM
539 pp = postProcess_SSE2;
541 pp = postProcess_altivec;
552 "Available postprocessing filters:\n"
554 "short long name short long option Description\n"
555 "* * a autoq CPU power dependent enabler\n"
556 " c chrom chrominance filtering enabled\n"
557 " y nochrom chrominance filtering disabled\n"
558 " n noluma luma filtering disabled\n"
559 "hb hdeblock (2 threshold) horizontal deblocking filter\n"
560 " 1. difference factor: default=32, higher -> more deblocking\n"
561 " 2. flatness threshold: default=39, lower -> more deblocking\n"
562 " the h & v deblocking filters share these\n"
563 " so you can't set different thresholds for h / v\n"
564 "vb vdeblock (2 threshold) vertical deblocking filter\n"
565 "ha hadeblock (2 threshold) horizontal deblocking filter\n"
566 "va vadeblock (2 threshold) vertical deblocking filter\n"
567 "h1 x1hdeblock experimental h deblock filter 1\n"
568 "v1 x1vdeblock experimental v deblock filter 1\n"
569 "dr dering deringing filter\n"
570 "al autolevels automatic brightness / contrast\n"
571 " f fullyrange stretch luminance to (0..255)\n"
572 "lb linblenddeint linear blend deinterlacer\n"
573 "li linipoldeint linear interpolating deinterlace\n"
574 "ci cubicipoldeint cubic interpolating deinterlacer\n"
575 "md mediandeint median deinterlacer\n"
576 "fd ffmpegdeint ffmpeg deinterlacer\n"
577 "l5 lowpass5 FIR lowpass deinterlacer\n"
578 "de default hb:a,vb:a,dr:a\n"
579 "fa fast h1:a,v1:a,dr:a\n"
580 "ac ha:a:128:7,va:a,dr:a\n"
581 "tn tmpnoise (3 threshold) temporal noise reducer\n"
582 " 1. <= 2. <= 3. larger -> stronger filtering\n"
583 "fq forceQuant <quantizer> force quantizer\n"
585 "<filterName>[:<option>[:<option>...]][[,|/][-]<filterName>[:<option>...]]...\n"
586 "long form example:\n"
587 "vdeblock:autoq/hdeblock:autoq/linblenddeint default,-vdeblock\n"
588 "short form example:\n"
589 "vb:a/hb:a/lb de,-vb\n"
599 static const char filterDelimiters[] =
",/";
600 static const char optionDelimiters[] =
":|";
609 if (!strcmp(
name,
"help")) {
611 for (p =
pp_help; strchr(p,
'\n'); p = strchr(p,
'\n') + 1) {
640 const char *filterName;
648 int numOfUnknownOptions=0;
652 filterToken=
av_strtok(p, filterDelimiters, &tokstate);
653 if(!filterToken)
break;
654 p+= strlen(filterToken) + 1;
655 filterName=
av_strtok(filterToken, optionDelimiters, &tokstate);
662 if(*filterName ==
'-'){
673 else if(!strcmp(
"nochrom",
option) || !strcmp(
"y",
option)) chrom=0;
674 else if(!strcmp(
"chrom",
option) || !strcmp(
"c",
option)) chrom=1;
675 else if(!strcmp(
"noluma",
option) || !strcmp(
"n",
option)) luma=0;
678 numOfUnknownOptions++;
694 spaceLeft= p -
temp + plen;
699 memmove(p + newlen, p, plen+1);
706 if( !strcmp(
filters[
i].longName, filterName)
707 || !strcmp(
filters[
i].shortName, filterName)){
714 if(q >=
filters[
i].minLumQuality && luma)
716 if(chrom==1 || (chrom==-1 &&
filters[
i].chromDefault))
725 if( !strcmp(
options[o],
"fullyrange")
729 numOfUnknownOptions--;
744 numOfUnknownOptions--;
745 if(numOfNoises >= 3)
break;
753 for(o=0;
options[o] && o<2; o++){
758 numOfUnknownOptions--;
767 for(o=0;
options[o] && o<1; o++){
772 numOfUnknownOptions--;
778 if(!filterNameOk) ppMode->
error++;
779 ppMode->
error += numOfUnknownOptions;
801 int mbWidth = (
width+15)>>4;
802 int mbHeight= (
height+15)>>4;
806 c->qpStride= qpStride;
822 reallocAlign((
void **)&
c->nonBQPTable, qpStride*mbHeight*
sizeof(int8_t));
823 reallocAlign((
void **)&
c->stdQPTable, qpStride*mbHeight*
sizeof(int8_t));
824 reallocAlign((
void **)&
c->forcedQPTable, mbWidth*
sizeof(int8_t));
836 int qpStride= (
width+15)/16 + 2;
843 c->hChromaSubSample= cpuCaps&0x3;
844 c->vChromaSubSample= (cpuCaps>>4)&0x3;
846 c->hChromaSubSample= 1;
847 c->vChromaSubSample= 1;
887 uint8_t *
dst[3],
const int dstStride[3],
889 const int8_t *QP_store,
int QPStride,
890 pp_mode *vm,
void *vc,
int pict_type)
892 int mbWidth = (
width+15)>>4;
893 int mbHeight= (
height+15)>>4;
897 int absQPStride =
FFABS(QPStride);
900 if(
c->stride < minStride ||
c->qpStride < absQPStride)
902 FFMAX(minStride,
c->stride),
903 FFMAX(
c->qpStride, absQPStride));
907 QP_store=
c->forcedQPTable;
908 absQPStride = QPStride = 0;
910 for(
i=0;
i<mbWidth;
i++)
c->forcedQPTable[
i]=
mode->forcedQuant;
912 for(
i=0;
i<mbWidth;
i++)
c->forcedQPTable[
i]= 1;
917 const int count=
FFMAX(mbHeight * absQPStride, mbWidth);
918 for(
i=0;
i<(count>>2);
i++){
921 for(
i<<=2;
i<count;
i++){
922 c->stdQPTable[
i] = QP_store[
i]>>1;
924 QP_store=
c->stdQPTable;
925 QPStride= absQPStride;
930 for(y=0; y<mbHeight; y++){
931 for(x=0; x<mbWidth; x++){
939 if((pict_type&7)!=3){
942 const int count=
FFMAX(mbHeight * QPStride, mbWidth);
943 for(
i=0;
i<(count>>2);
i++){
946 for(
i<<=2;
i<count;
i++){
947 c->nonBQPTable[
i] = QP_store[
i] & 0x3F;
951 for(
i=0;
i<mbHeight;
i++) {
952 for(j=0; j<absQPStride; j++) {
953 c->nonBQPTable[
i*absQPStride+j] = QP_store[
i*QPStride+j] & 0x3F;
977 else if(srcStride[1] == dstStride[1] && srcStride[2] == dstStride[2]){
983 memcpy(&(
dst[1][y*dstStride[1]]), &(
src[1][y*srcStride[1]]),
width);
984 memcpy(&(
dst[2][y*dstStride[2]]), &(
src[2][y*srcStride[2]]),
width);
pp_mode * pp_get_mode_by_name_and_quality(const char *name, int quality)
Return a pp_mode or NULL if an error occurred.
#define FFMPEG_DEINT_FILTER
it s the only field you need to keep assuming you have a context There is some magic you don t need to care about around this just let it vf default minimum maximum flags name is the option name
static void reallocAlign(void **p, int size)
static const AVClass av_codec_context_class
static const struct PPFilter filters[]
static const char *const replaceTable[]
trying all byte sequences megabyte in length and selecting the best looking sequence will yield cases to try But a word about which is also called distortion Distortion can be quantified by almost any quality measurement one chooses the sum of squared differences is used but more complex methods that consider psychovisual effects can be used as well It makes no difference in this discussion First step
#define LOWPASS5_DEINT_FILTER
static void horizX1Filter(uint8_t *src, int stride, int QP)
Experimental Filter 1 (Horizontal) will not damage linear gradients Flat blocks should look like they...
int av_get_cpu_flags(void)
Return the flags which specify extensions supported by the CPU.
int mask
Bitmask to turn this filter on.
trying all byte sequences megabyte in length and selecting the best looking sequence will yield cases to try But a word about quality
#define PP_PICT_TYPE_QP2
MPEG2 style QScale.
int chromMode
activates filters for chrominance
static int isHorizMinMaxOk_C(const uint8_t src[], int stride, int QP)
static double val(void *priv, double ch)
av_cold void pp_free_context(void *vc)
s EdgeDetect Foobar g libavfilter vf_edgedetect c libavfilter vf_foobar c edit libavfilter and add an entry for foobar following the pattern of the other filters edit libavfilter allfilters and add an entry for foobar following the pattern of the other filters configure make j< whatever > ffmpeg ffmpeg i you should get a foobar png with Lena edge detected That s your new playground is ready Some little details about what s going which in turn will define variables for the build system and the C
trying all byte sequences megabyte in length and selecting the best looking sequence will yield cases to try But first
#define AV_LOG_ERROR
Something went wrong and cannot losslessly be recovered.
#define FF_ARRAY_ELEMS(a)
void pp_free_mode(pp_mode *mode)
static void postProcess(const uint8_t src[], int srcStride, uint8_t dst[], int dstStride, int width, int height, const int8_t QPs[], int QPStride, int isColor, pp_mode *vm, pp_context *vc)
void pp_postprocess(const uint8_t *src[3], const int srcStride[3], uint8_t *dst[3], const int dstStride[3], int width, int height, const int8_t *QP_store, int QPStride, pp_mode *vm, void *vc, int pict_type)
char * av_strtok(char *s, const char *delim, char **saveptr)
Split the string into several tokens which can be accessed by successive calls to av_strtok().
const char pp_help[]
a simple help text
#define AV_LOG_DEBUG
Stuff which is only useful for libav* developers.
#define TEMP_NOISE_FILTER
#define FFABS(a)
Absolute value, Note, INT_MIN / INT64_MIN result in undefined behavior as they are not representable ...
av_cold pp_context * pp_get_context(int width, int height, int cpuCaps)
static int horizClassify_C(const uint8_t src[], int stride, const PPContext *c)
static const char * context_to_name(void *ptr)
static void doHorizDefFilter_C(uint8_t dst[], int stride, const PPContext *c)
Describe the class of an AVClass context structure.
Rational number (pair of numerator and denominator).
#define MEDIAN_DEINT_FILTER
static void linecpy(void *dest, const void *src, int lines, int stride)
static void reallocBuffers(PPContext *c, int width, int height, int stride, int qpStride)
#define GET_MODE_BUFFER_SIZE
#define AV_CPU_FLAG_ALTIVEC
standard
Undefined Behavior In the C some operations are like signed integer dereferencing freed accessing outside allocated Undefined Behavior must not occur in a C it is not safe even if the output of undefined operations is unused The unsafety may seem nit picking but Optimizing compilers have in fact optimized code on the assumption that no undefined Behavior occurs Optimizing code based on wrong assumptions can and has in some cases lead to effects beyond the output of computations The signed integer overflow problem in speed critical code Code which is highly optimized and works with signed integers sometimes has the problem that often the output of the computation does not c
#define AV_CPU_FLAG_SSE2
PIV SSE2 functions.
uint8_t ptrdiff_t const uint8_t ptrdiff_t int intptr_t intptr_t int int16_t * dst
static int isVertMinMaxOk_C(const uint8_t src[], int stride, int QP)
The reader does not expect b to be semantically here and if the code is changed by maybe adding a a division or other the signedness will almost certainly be mistaken To avoid this confusion a new type was SUINT is the C unsigned type but it holds a signed int to use the same example SUINT a
#define AV_LOG_INFO
Standard information.
static av_always_inline void do_a_deblock_C(uint8_t *src, int step, int stride, const PPContext *c, int mode)
accurate deblock filter
#define i(width, name, range_min, range_max)
DECLARE_ASM_CONST(16, double, pd_1)[2]
int minAllowedY
for brightness correction
void * av_mallocz(size_t size)
Allocate a memory block with alignment suitable for all memory accesses (including vectors if availab...
#define CUBIC_IPOL_DEINT_FILTER
#define PP_CPU_CAPS_ALTIVEC
void(* pp_fn)(const uint8_t src[], int srcStride, uint8_t dst[], int dstStride, int width, int height, const int8_t QPs[], int QPStride, int isColor, PPContext *c2)
static int isHorizDC_C(const uint8_t src[], int stride, const PPContext *c)
Check if the given 8x8 Block is mostly "flat".
static void doHorizLowPass_C(uint8_t dst[], int stride, const PPContext *c)
Do a horizontal low pass filter on the 10x8 block (dst points to middle 8x8 Block) using the 9-Tap Fi...
#define LINEAR_BLEND_DEINT_FILTER
int error
non zero on error
static int vertClassify_C(const uint8_t src[], int stride, const PPContext *c)
AVRational maxClippedThreshold
amount of "black" you are willing to lose to get a brightness-corrected picture
#define LINEAR_IPOL_DEINT_FILTER
static int isVertDC_C(const uint8_t src[], int stride, const PPContext *c)
Check if the middle 8x8 Block in the given 8x16 block is flat.
int maxTmpNoise[3]
for Temporal Noise Reducing filter (Maximal sum of abs differences)
size_t av_strlcpy(char *dst, const char *src, size_t size)
Copy the string src to dst, but no more than size - 1 bytes, and null-terminate dst.
#define OPTIONS_ARRAY_SIZE
#define LEVEL_FIX
Brightness & Contrast.
int forcedQuant
quantizer if FORCE_QUANT is used
int lumMode
activates filters for luminance
int maxAllowedY
for brightness correction