[FFmpeg-devel] [PATCH] lavfi: use ceil right shift for chroma width/height.
Clément Bœsch
ubitux at gmail.com
Thu May 9 18:14:34 CEST 2013
This should fix several issues with odd dimensions inputs.
---
Note: this is mostly untested
---
libavfilter/vf_blend.c | 4 ++--
libavfilter/vf_boxblur.c | 2 +-
libavfilter/vf_decimate.c | 4 ++--
libavfilter/vf_delogo.c | 6 ++++--
libavfilter/vf_extractplanes.c | 4 ++--
libavfilter/vf_fade.c | 3 ++-
libavfilter/vf_fieldmatch.c | 8 ++++----
libavfilter/vf_geq.c | 8 ++++----
libavfilter/vf_hflip.c | 20 ++++++++++----------
libavfilter/vf_hqdn3d.c | 4 ++--
libavfilter/vf_hue.c | 3 ++-
libavfilter/vf_il.c | 2 +-
libavfilter/vf_interlace.c | 2 +-
libavfilter/vf_kerndeint.c | 2 +-
libavfilter/vf_mpdecimate.c | 3 ++-
libavfilter/vf_noise.c | 2 +-
libavfilter/vf_showinfo.c | 2 +-
libavfilter/vf_smartblur.c | 7 ++++---
libavfilter/vf_telecine.c | 2 +-
libavfilter/vf_tinterlace.c | 2 +-
libavfilter/vf_transpose.c | 4 ++--
21 files changed, 50 insertions(+), 44 deletions(-)
diff --git a/libavfilter/vf_blend.c b/libavfilter/vf_blend.c
index b4c62ba..a0022cd 100644
--- a/libavfilter/vf_blend.c
+++ b/libavfilter/vf_blend.c
@@ -372,8 +372,8 @@ static void blend_frame(AVFilterContext *ctx,
for (plane = 0; plane < b->nb_planes; plane++) {
int hsub = plane == 1 || plane == 2 ? b->hsub : 0;
int vsub = plane == 1 || plane == 2 ? b->vsub : 0;
- int outw = dst_buf->width >> hsub;
- int outh = dst_buf->height >> vsub;
+ int outw = FF_CEIL_RSHIFT(dst_buf->width, hsub);
+ int outh = FF_CEIL_RSHIFT(dst_buf->height, vsub);
uint8_t *dst = dst_buf->data[plane];
uint8_t *top = top_buf->data[plane];
uint8_t *bottom = bottom_buf->data[plane];
diff --git a/libavfilter/vf_boxblur.c b/libavfilter/vf_boxblur.c
index b010670..a8a2014 100644
--- a/libavfilter/vf_boxblur.c
+++ b/libavfilter/vf_boxblur.c
@@ -302,7 +302,7 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *in)
AVFilterLink *outlink = inlink->dst->outputs[0];
AVFrame *out;
int plane;
- int cw = inlink->w >> boxblur->hsub, ch = in->height >> boxblur->vsub;
+ int cw = FF_CEIL_RSHIFT(inlink->w, boxblur->hsub), ch = FF_CEIL_RSHIFT(in->height, boxblur->vsub);
int w[4] = { inlink->w, cw, cw, inlink->w };
int h[4] = { in->height, ch, ch, in->height };
diff --git a/libavfilter/vf_decimate.c b/libavfilter/vf_decimate.c
index 9548531..8767d5f 100644
--- a/libavfilter/vf_decimate.c
+++ b/libavfilter/vf_decimate.c
@@ -92,8 +92,8 @@ static void calc_diffs(const DecimateContext *dm, struct qitem *q,
const int linesize2 = f2->linesize[plane];
const uint8_t *f1p = f1->data[plane];
const uint8_t *f2p = f2->data[plane];
- int width = plane ? f1->width >> dm->hsub : f1->width;
- int height = plane ? f1->height >> dm->vsub : f1->height;
+ int width = plane ? FF_CEIL_RSHIFT(f1->width, dm->hsub) : f1->width;
+ int height = plane ? FF_CEIL_RSHIFT(f1->height, dm->vsub) : f1->height;
int hblockx = dm->blockx / 2;
int hblocky = dm->blocky / 2;
diff --git a/libavfilter/vf_delogo.c b/libavfilter/vf_delogo.c
index c747b02..b644190 100644
--- a/libavfilter/vf_delogo.c
+++ b/libavfilter/vf_delogo.c
@@ -228,9 +228,11 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *in)
apply_delogo(out->data[plane], out->linesize[plane],
in ->data[plane], in ->linesize[plane],
- inlink->w>>hsub, inlink->h>>vsub,
+ FF_CEIL_RSHIFT(inlink->w, hsub),
+ FF_CEIL_RSHIFT(inlink->h, vsub),
delogo->x>>hsub, delogo->y>>vsub,
- delogo->w>>hsub, delogo->h>>vsub,
+ FF_CEIL_RSHIFT(delogo->w, hsub),
+ FF_CEIL_RSHIFT(delogo->h, vsub),
delogo->band>>FFMIN(hsub, vsub),
delogo->show, direct);
}
diff --git a/libavfilter/vf_extractplanes.c b/libavfilter/vf_extractplanes.c
index 229e3d5..9844ed5 100644
--- a/libavfilter/vf_extractplanes.c
+++ b/libavfilter/vf_extractplanes.c
@@ -171,8 +171,8 @@ static int config_output(AVFilterLink *outlink)
const int output = outlink->srcpad - ctx->output_pads;
if (e->map[output] == 1 || e->map[output] == 2) {
- outlink->h = inlink->h >> desc->log2_chroma_h;
- outlink->w = inlink->w >> desc->log2_chroma_w;
+ outlink->h = FF_CEIL_RSHIFT(inlink->h, desc->log2_chroma_h);
+ outlink->w = FF_CEIL_RSHIFT(inlink->w, desc->log2_chroma_w);
}
return 0;
diff --git a/libavfilter/vf_fade.c b/libavfilter/vf_fade.c
index 4dbd4c7..4f7039e 100644
--- a/libavfilter/vf_fade.c
+++ b/libavfilter/vf_fade.c
@@ -233,8 +233,9 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *frame)
/* chroma planes */
for (plane = 1; plane < 3; plane++) {
for (i = 0; i < frame->height; i++) {
+ const int width = FF_CEIL_RSHIFT(inlink->w, fade->hsub);
p = frame->data[plane] + (i >> fade->vsub) * frame->linesize[plane];
- for (j = 0; j < inlink->w >> fade->hsub; j++) {
+ for (j = 0; j < width; j++) {
/* 8421367 = ((128 << 1) + 1) << 15. It is an integer
* representation of 128.5. The .5 is for rounding
* purposes. */
diff --git a/libavfilter/vf_fieldmatch.c b/libavfilter/vf_fieldmatch.c
index 3495895..3a6f806 100644
--- a/libavfilter/vf_fieldmatch.c
+++ b/libavfilter/vf_fieldmatch.c
@@ -153,12 +153,12 @@ AVFILTER_DEFINE_CLASS(fieldmatch);
static int get_width(const FieldMatchContext *fm, const AVFrame *f, int plane)
{
- return plane ? f->width >> fm->hsub : f->width;
+ return plane ? FF_CEIL_RSHIFT(f->width, fm->hsub) : f->width;
}
static int get_height(const FieldMatchContext *fm, const AVFrame *f, int plane)
{
- return plane ? f->height >> fm->vsub : f->height;
+ return plane ? FF_CEIL_RSHIFT(f->height, fm->vsub) : f->height;
}
static int64_t luma_abs_diff(const AVFrame *f1, const AVFrame *f2)
@@ -270,8 +270,8 @@ static int calc_combed_score(const FieldMatchContext *fm, const AVFrame *src)
uint8_t *cmkp = fm->cmask_data[0];
uint8_t *cmkpU = fm->cmask_data[1];
uint8_t *cmkpV = fm->cmask_data[2];
- const int width = src->width >> fm->hsub;
- const int height = src->height >> fm->vsub;
+ const int width = FF_CEIL_RSHIFT(src->width, fm->hsub);
+ const int height = FF_CEIL_RSHIFT(src->height, fm->vsub);
const int cmk_linesize = fm->cmask_linesize[0] << 1;
const int cmk_linesizeUV = fm->cmask_linesize[2];
uint8_t *cmkpp = cmkp - (cmk_linesize>>1);
diff --git a/libavfilter/vf_geq.c b/libavfilter/vf_geq.c
index a5396f8..5ee75d1 100644
--- a/libavfilter/vf_geq.c
+++ b/libavfilter/vf_geq.c
@@ -66,8 +66,8 @@ static inline double getpix(void *priv, double x, double y, int plane)
AVFrame *picref = geq->picref;
const uint8_t *src = picref->data[plane];
const int linesize = picref->linesize[plane];
- const int w = picref->width >> ((plane == 1 || plane == 2) ? geq->hsub : 0);
- const int h = picref->height >> ((plane == 1 || plane == 2) ? geq->vsub : 0);
+ const int w = (plane == 1 || plane == 2) ? FF_CEIL_RSHIFT(picref->width, geq->hsub) : picref->width;
+ const int h = (plane == 1 || plane == 2) ? FF_CEIL_RSHIFT(picref->height, geq->vsub) : picref->height;
if (!src)
return 0;
@@ -209,8 +209,8 @@ static int geq_filter_frame(AVFilterLink *inlink, AVFrame *in)
int x, y;
uint8_t *dst = out->data[plane];
const int linesize = out->linesize[plane];
- const int w = inlink->w >> ((plane == 1 || plane == 2) ? geq->hsub : 0);
- const int h = inlink->h >> ((plane == 1 || plane == 2) ? geq->vsub : 0);
+ const int w = (plane == 1 || plane == 2) ? FF_CEIL_RSHIFT(inlink->w, geq->hsub) : inlink->w;
+ const int h = (plane == 1 || plane == 2) ? FF_CEIL_RSHIFT(inlink->h, geq->vsub) : inlink->h;
values[VAR_W] = w;
values[VAR_H] = h;
diff --git a/libavfilter/vf_hflip.c b/libavfilter/vf_hflip.c
index cb51981..0250b43 100644
--- a/libavfilter/vf_hflip.c
+++ b/libavfilter/vf_hflip.c
@@ -77,7 +77,7 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *in)
AVFilterLink *outlink = ctx->outputs[0];
AVFrame *out;
uint8_t *inrow, *outrow;
- int i, j, plane, step, hsub, vsub;
+ int i, j, plane, step;
out = ff_get_video_buffer(outlink, outlink->w, outlink->h);
if (!out) {
@@ -91,16 +91,16 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *in)
memcpy(out->data[1], in->data[1], AVPALETTE_SIZE);
for (plane = 0; plane < 4 && in->data[plane]; plane++) {
+ const int width = (plane == 1 || plane == 2) ? FF_CEIL_RSHIFT(inlink->w, flip->hsub) : inlink->w;
+ const int height = (plane == 1 || plane == 2) ? FF_CEIL_RSHIFT(inlink->h, flip->vsub) : inlink->h;
step = flip->max_step[plane];
- hsub = (plane == 1 || plane == 2) ? flip->hsub : 0;
- vsub = (plane == 1 || plane == 2) ? flip->vsub : 0;
outrow = out->data[plane];
- inrow = in ->data[plane] + ((inlink->w >> hsub) - 1) * step;
- for (i = 0; i < in->height >> vsub; i++) {
+ inrow = in ->data[plane] + (width - 1) * step;
+ for (i = 0; i < height; i++) {
switch (step) {
case 1:
- for (j = 0; j < (inlink->w >> hsub); j++)
+ for (j = 0; j < width; j++)
outrow[j] = inrow[-j];
break;
@@ -108,7 +108,7 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *in)
{
uint16_t *outrow16 = (uint16_t *)outrow;
uint16_t * inrow16 = (uint16_t *) inrow;
- for (j = 0; j < (inlink->w >> hsub); j++)
+ for (j = 0; j < width; j++)
outrow16[j] = inrow16[-j];
}
break;
@@ -117,7 +117,7 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *in)
{
uint8_t *in = inrow;
uint8_t *out = outrow;
- for (j = 0; j < (inlink->w >> hsub); j++, out += 3, in -= 3) {
+ for (j = 0; j < width; j++, out += 3, in -= 3) {
int32_t v = AV_RB24(in);
AV_WB24(out, v);
}
@@ -128,13 +128,13 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *in)
{
uint32_t *outrow32 = (uint32_t *)outrow;
uint32_t * inrow32 = (uint32_t *) inrow;
- for (j = 0; j < (inlink->w >> hsub); j++)
+ for (j = 0; j < width; j++)
outrow32[j] = inrow32[-j];
}
break;
default:
- for (j = 0; j < (inlink->w >> hsub); j++)
+ for (j = 0; j < width; j++)
memcpy(outrow + j*step, inrow - j*step, step);
}
diff --git a/libavfilter/vf_hqdn3d.c b/libavfilter/vf_hqdn3d.c
index 51adeb8..8e8f553 100644
--- a/libavfilter/vf_hqdn3d.c
+++ b/libavfilter/vf_hqdn3d.c
@@ -297,8 +297,8 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *in)
for (c = 0; c < 3; c++) {
denoise(hqdn3d, in->data[c], out->data[c],
hqdn3d->line, &hqdn3d->frame_prev[c],
- in->width >> (!!c * hqdn3d->hsub),
- in->height >> (!!c * hqdn3d->vsub),
+ FF_CEIL_RSHIFT(in->width, (!!c * hqdn3d->hsub)),
+ FF_CEIL_RSHIFT(in->height, (!!c * hqdn3d->vsub)),
in->linesize[c], out->linesize[c],
hqdn3d->coefs[c?2:0], hqdn3d->coefs[c?3:1]);
}
diff --git a/libavfilter/vf_hue.c b/libavfilter/vf_hue.c
index c62cba8..cba39d0 100644
--- a/libavfilter/vf_hue.c
+++ b/libavfilter/vf_hue.c
@@ -305,7 +305,8 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *inpic)
process_chrominance(outpic->data[1], outpic->data[2], outpic->linesize[1],
inpic->data[1], inpic->data[2], inpic->linesize[1],
- inlink->w >> hue->hsub, inlink->h >> hue->vsub,
+ FF_CEIL_RSHIFT(inlink->w, hue->hsub),
+ FF_CEIL_RSHIFT(inlink->h, hue->vsub),
hue->hue_cos, hue->hue_sin);
if (!direct)
diff --git a/libavfilter/vf_il.c b/libavfilter/vf_il.c
index 7edd042..783b91a 100644
--- a/libavfilter/vf_il.c
+++ b/libavfilter/vf_il.c
@@ -110,7 +110,7 @@ static int config_input(AVFilterLink *inlink)
if ((ret = av_image_fill_linesizes(il->linesize, inlink->format, inlink->w)) < 0)
return ret;
- il->chroma_height = inlink->h >> desc->log2_chroma_h;
+ il->chroma_height = FF_CEIL_RSHIFT(inlink->h, desc->log2_chroma_h);
return 0;
}
diff --git a/libavfilter/vf_interlace.c b/libavfilter/vf_interlace.c
index 3e787ab..3315fb0 100644
--- a/libavfilter/vf_interlace.c
+++ b/libavfilter/vf_interlace.c
@@ -131,7 +131,7 @@ static void copy_picture_field(AVFrame *src_frame, AVFrame *dst_frame,
int plane, i, j;
for (plane = 0; plane < desc->nb_components; plane++) {
- int lines = (plane == 1 || plane == 2) ? inlink->h >> vsub : inlink->h;
+ int lines = (plane == 1 || plane == 2) ? FF_CEIL_RSHIFT(inlink->h, vsub) : inlink->h;
int linesize = av_image_get_linesize(inlink->format, inlink->w, plane);
uint8_t *dstp = dst_frame->data[plane];
const uint8_t *srcp = src_frame->data[plane];
diff --git a/libavfilter/vf_kerndeint.c b/libavfilter/vf_kerndeint.c
index 8a44868..431a0a9 100644
--- a/libavfilter/vf_kerndeint.c
+++ b/libavfilter/vf_kerndeint.c
@@ -151,7 +151,7 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *inpic)
outpic->interlaced_frame = 0;
for (plane = 0; inpic->data[plane] && plane < 4; plane++) {
- h = plane == 0 ? inlink->h : inlink->h >> kerndeint->vsub;
+ h = plane == 0 ? inlink->h : FF_CEIL_RSHIFT(inlink->h, kerndeint->vsub);
bwidth = kerndeint->tmp_bwidth[plane];
srcp = srcp_saved = inpic->data[plane];
diff --git a/libavfilter/vf_mpdecimate.c b/libavfilter/vf_mpdecimate.c
index 2e386f7..45d510b 100644
--- a/libavfilter/vf_mpdecimate.c
+++ b/libavfilter/vf_mpdecimate.c
@@ -122,7 +122,8 @@ static int decimate_frame(AVFilterContext *ctx,
int hsub = plane == 1 || plane == 2 ? decimate->hsub : 0;
if (diff_planes(ctx,
cur->data[plane], ref->data[plane], ref->linesize[plane],
- ref->width>>hsub, ref->height>>vsub))
+ FF_CEIL_RSHIFT(ref->width, hsub),
+ FF_CEIL_RSHIFT(ref->height, vsub)))
return 0;
}
diff --git a/libavfilter/vf_noise.c b/libavfilter/vf_noise.c
index c965cbf..da418fe 100644
--- a/libavfilter/vf_noise.c
+++ b/libavfilter/vf_noise.c
@@ -193,7 +193,7 @@ static int config_input(AVFilterLink *inlink)
if ((ret = av_image_fill_linesizes(n->linesize, inlink->format, inlink->w)) < 0)
return ret;
- n->height[1] = n->height[2] = inlink->h >> desc->log2_chroma_h;
+ n->height[1] = n->height[2] = FF_CEIL_RSHIFT(inlink->h, desc->log2_chroma_h);
n->height[0] = n->height[3] = inlink->h;
return 0;
diff --git a/libavfilter/vf_showinfo.c b/libavfilter/vf_showinfo.c
index dd97843..9acadcf 100644
--- a/libavfilter/vf_showinfo.c
+++ b/libavfilter/vf_showinfo.c
@@ -46,7 +46,7 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *frame)
for (plane = 0; plane < 4 && frame->data[plane]; plane++) {
int64_t linesize = av_image_get_linesize(frame->format, frame->width, plane);
uint8_t *data = frame->data[plane];
- int h = plane == 1 || plane == 2 ? inlink->h >> vsub : inlink->h;
+ int h = plane == 1 || plane == 2 ? FF_CEIL_RSHIFT(inlink->h, vsub) : inlink->h;
if (linesize < 0)
return linesize;
diff --git a/libavfilter/vf_smartblur.c b/libavfilter/vf_smartblur.c
index 4dd1664..daf7451 100644
--- a/libavfilter/vf_smartblur.c
+++ b/libavfilter/vf_smartblur.c
@@ -166,7 +166,8 @@ static int config_props(AVFilterLink *inlink)
alloc_sws_context(&sblur->luma, inlink->w, inlink->h, sblur->sws_flags);
alloc_sws_context(&sblur->chroma,
- inlink->w >> sblur->hsub, inlink->h >> sblur->vsub,
+ FF_CEIL_RSHIFT(inlink->w, sblur->hsub),
+ FF_CEIL_RSHIFT(inlink->h, sblur->vsub),
sblur->sws_flags);
return 0;
@@ -241,8 +242,8 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *inpic)
SmartblurContext *sblur = inlink->dst->priv;
AVFilterLink *outlink = inlink->dst->outputs[0];
AVFrame *outpic;
- int cw = inlink->w >> sblur->hsub;
- int ch = inlink->h >> sblur->vsub;
+ int cw = FF_CEIL_RSHIFT(inlink->w, sblur->hsub);
+ int ch = FF_CEIL_RSHIFT(inlink->h, sblur->vsub);
outpic = ff_get_video_buffer(outlink, outlink->w, outlink->h);
if (!outpic) {
diff --git a/libavfilter/vf_telecine.c b/libavfilter/vf_telecine.c
index e30f357..ba47da1 100644
--- a/libavfilter/vf_telecine.c
+++ b/libavfilter/vf_telecine.c
@@ -129,7 +129,7 @@ static int config_input(AVFilterLink *inlink)
if ((ret = av_image_fill_linesizes(tc->stride, inlink->format, inlink->w)) < 0)
return ret;
- tc->planeheight[1] = tc->planeheight[2] = inlink->h >> desc->log2_chroma_h;
+ tc->planeheight[1] = tc->planeheight[2] = FF_CEIL_RSHIFT(inlink->h, desc->log2_chroma_h);
tc->planeheight[0] = tc->planeheight[3] = inlink->h;
tc->nb_planes = av_pix_fmt_count_planes(inlink->format);
diff --git a/libavfilter/vf_tinterlace.c b/libavfilter/vf_tinterlace.c
index f6bf054..5e89162 100644
--- a/libavfilter/vf_tinterlace.c
+++ b/libavfilter/vf_tinterlace.c
@@ -130,7 +130,7 @@ static int config_out_props(AVFilterLink *outlink)
/* fill black picture with black */
for (i = 0; i < 4 && tinterlace->black_data[i]; i++) {
- int h = i == 1 || i == 2 ? outlink->h >> desc->log2_chroma_h : outlink->h;
+ int h = i == 1 || i == 2 ? FF_CEIL_RSHIFT(outlink->h, desc->log2_chroma_h) : outlink->h;
memset(tinterlace->black_data[i], black[i],
tinterlace->black_linesize[i] * h);
}
diff --git a/libavfilter/vf_transpose.c b/libavfilter/vf_transpose.c
index bd66a61..c949e07 100644
--- a/libavfilter/vf_transpose.c
+++ b/libavfilter/vf_transpose.c
@@ -163,8 +163,8 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *in)
int vsub = plane == 1 || plane == 2 ? trans->vsub : 0;
int pixstep = trans->pixsteps[plane];
int inh = in->height >> vsub;
- int outw = out->width >> hsub;
- int outh = out->height >> vsub;
+ int outw = FF_CEIL_RSHIFT(out->width, hsub);
+ int outh = FF_CEIL_RSHIFT(out->height, vsub);
uint8_t *dst, *src;
int dstlinesize, srclinesize;
int x, y;
--
1.8.2.2
More information about the ffmpeg-devel
mailing list