Re: [Pixman] [PATCH 13/14] pixman-filter: Nested polynomial for cubic

2016-04-12 Thread Bill Spitzak
Because the integral function is relying on the range being clamped to the
non-zero portion for impulse filters and for box, and range checks are
missing for some of the other filter functions, I would be tempted to
remove the range check from here, and also from the impulse function (it
would return 1 for all x). Oded did not like that idea but I wonder if you
have any opinion.

On Mon, Apr 11, 2016 at 7:36 PM, Søren Sandmann Pedersen <
soren.sandm...@gmail.com> wrote:

> From: Bill Spitzak 
>
> v11: Restored range checks
>
> Signed-off-by: Bill Spitzak 
> Reviewed-by: Oded Gabbay 
> ---
>  pixman/pixman-filter.c | 14 --
>  1 file changed, 8 insertions(+), 6 deletions(-)
>
> diff --git a/pixman/pixman-filter.c b/pixman/pixman-filter.c
> index 4abd05f..db4ab6e 100644
> --- a/pixman/pixman-filter.c
> +++ b/pixman/pixman-filter.c
> @@ -109,14 +109,16 @@ general_cubic (double x, double B, double C)
>
>  if (ax < 1)
>  {
> -   return ((12 - 9 * B - 6 * C) * ax * ax * ax +
> -   (-18 + 12 * B + 6 * C) * ax * ax + (6 - 2 * B)) / 6;
> +   return (((12 - 9 * B - 6 * C) * ax +
> +(-18 + 12 * B + 6 * C)) * ax * ax +
> +   (6 - 2 * B)) / 6;
>  }
> -else if (ax >= 1 && ax < 2)
> +else if (ax < 2)
>  {
> -   return ((-B - 6 * C) * ax * ax * ax +
> -   (6 * B + 30 * C) * ax * ax + (-12 * B - 48 * C) *
> -   ax + (8 * B + 24 * C)) / 6;
> +   return -B - 6 * C) * ax +
> + (6 * B + 30 * C)) * ax +
> +(-12 * B - 48 * C)) * ax +
> +   (8 * B + 24 * C)) / 6;
>  }
>  else
>  {
> --
> 1.7.11.7
>
>
___
Pixman mailing list
Pixman@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/pixman


Re: [Pixman] [PATCH 12/14] pixman-filter: Fix several issues related to normalization

2016-04-12 Thread Bill Spitzak
Excellent idea to put the error diffusion into the division. Just a bit of
cleanup and changes for some suspected bugs (that are probably invisible
but might as well get them):

On Mon, Apr 11, 2016 at 7:36 PM, Søren Sandmann Pedersen <
soren.sandm...@gmail.com> wrote:

> There are a few bugs in the current normalization code
>
> (1) The normalization is based on the sum of the *floating point*
> values generated by integral(). But in order to get the sum to be
> close to pixman_fixed_1, the sum of the rounded fixed point values
> should be used.
>
> (2) The multiplications in the normalization loops often round the
> same way, so the residual error can fairly large.
>
> (3) The residual error is added to the sample located at index
> (width - width / 2), which is not the midpoint for odd widths (and
> for width 1 is in fact outside the array).
>
> This patch fixes these issues by (1) using the sum of the fixed point
> values as the total to divide by, (2) doing error diffusion in the
> normalization loop, and (3) putting any residual error (which is now
> guaranteed to be less than pixman_fixed_e) at the first sample, which
> is the only one that didn't get any error diffused into it.
>
> Signed-off-by: Søren Sandmann 
> ---
>  pixman/pixman-filter.c | 23 +++
>  1 file changed, 15 insertions(+), 8 deletions(-)
>
> diff --git a/pixman/pixman-filter.c b/pixman/pixman-filter.c
> index 32aaa9a..4abd05f 100644
> --- a/pixman/pixman-filter.c
> +++ b/pixman/pixman-filter.c
> @@ -247,7 +247,7 @@ create_1d_filter (int  width,
>  double frac = step / 2.0 + i * step;
> pixman_fixed_t new_total;
>  int x, x1, x2;
> -   double total;
> +   double total, e;
>

I think total should be a pixman_fixed_t as that is what it is summing.


> /* Sample convolution of reconstruction and sampling
>  * filter. See rounding.txt regarding the rounding
> @@ -278,24 +278,31 @@ create_1d_filter (int  width,
>   ihigh - ilow);
> }
>
> -   total += c;
> -*p++ = (pixman_fixed_t)(c * 65536.0 + 0.5);
> +*p = (pixman_fixed_t)floor (c * 65536.0 + 0.5);
>

floor probably is a good idea to make negative filter entries work. Is
there a macro that does this conversion?

+   total += *p;
> +   p++;
>  }
>

Might want to skip the normalize if total==pixman_fixed_1, though perhaps a
test to see how often that happens would be informative.


>
> -   /* Normalize */
> +   /* Normalize, with error diffusion */
> p -= width;
> -total = 1 / total;
> +total = 65536.0 / total;
>

Remove the division so total can be a pixman_fixed_t.


>  new_total = 0;
> +   e = 0.0;
>

Change this to 0.5


> for (x = x1; x < x2; ++x)
> {
> -   pixman_fixed_t t = (*p) * total + 0.5;
> +   double v = (*p) * total + e;


Change to this so total can be a pixman_fixed_t:
   double v = (*p) * (double)(pixman_fixed_1) / total + e;

+   pixman_fixed_t t = floor (v + 0.5);
>

Change this to just floor(v). The 0.5 factor is incorporated into e. This
version is in effect adding .5 to all the samples, though that is
compensated for somewhat by floor in effect subtracting .5, but imagine
what happens if e > 0.5. This bug was in Nuke for many years btw.


> +   e = v - t;
> new_total += t;
> *p++ = t;
> }
>
> -   if (new_total != pixman_fixed_1)
> -   *(p - width / 2) += (pixman_fixed_1 - new_total);
> +   /* pixman_fixed_e's worth of error may remain; put it
> +* at the first sample, since that is the only one that
> +* hasn't had any error diffused into it.
> +*/
> +   *(p - width) += pixman_fixed_1 - new_total;
>

I'm not absolutely convinced that the first sample is best. Dumping this on
the central pixel may be better because that value is larger so the
relative change is smaller:

*(p - (width+1)/2) += pixman_fixed_1 - new_total;


>  }
>  }
>
> --
> 1.7.11.7
>
>
___
Pixman mailing list
Pixman@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/pixman


Re: [Pixman] [PATCH 07/14] pixman-image: Added enable-gnuplot config to view filters in gnuplot

2016-04-12 Thread Bill Spitzak
On Tue, Apr 12, 2016 at 1:55 PM, Søren Sandmann 
wrote:

>
>   1-wide filters - looks triangular, but a 1-wide box would be more
>>>accurate
>>>
>>
>> Because you are not plotting the two dummy points at (0,±width/2), a
>> 1-wide filter is actually just a single point.
>>
>> You may be right that leaving the dummy points off the plot may make it
>> easier to figure out what is going on.
>>
>
> Okay, I will update the comment.
>
> I don't like to make up fake data points, but maybe I should add
> [x=-width/2:width/2] to the gnuplot command line.
>

Yes that sounds like a very good idea.


>
> diff --git a/pixman/rounding.txt b/pixman/rounding.txt
>>
>>> index b52b084..1c00019 100644
>>> --- a/pixman/rounding.txt
>>> +++ b/pixman/rounding.txt
>>> @@ -160,6 +160,7 @@ which means the contents of the matrix corresponding
>>> to (frac) should
>>>  contain width samplings of the function, with the first sample at:
>>>
>>> floor (frac - (width - 1) / 2.0 - e) + 0.5 - frac
>>> + = ceil (frac - width / 2.0 - 0.5) + 0.5 - frac
>>>
>>
>> Unfortunately this produces numbers that don't agree with the filter
>> generator or filtering code.
>>
>> For a width==4 filter with n_phases==1, the generator seems to produce
>> values at -1, 0, 1, 2, so the first sample is at -1. It also appears the
>> filtering sampler is using the same rule, otherwise these filters would
>> produce an obvious shift in the image.
>>
>
> If you add printf's on top of this series
>
> diff --git a/pixman/pixman-filter.c b/pixman/pixman-filter.c
> index 176dfae..4a8743e 100644
> --- a/pixman/pixman-filter.c
> +++ b/pixman/pixman-filter.c
> @@ -129,12 +129,15 @@ general_cubic (double x, double B, double C)
>  static double
>  cubic_kernel (double x)
>  {
> +  double v = general_cubic (x, 1/3.0, 1/3.0);
> +
> +  printf ("cubic(%f) => %f\n", x, v);
>  /* This is the Mitchell-Netravali filter.
>   *
>   * (0.0, 0.5) would give us the Catmull-Rom spline,
>   * but that one seems to be indistinguishable from Lanczos2.
>   */
> -return general_cubic (x, 1/3.0, 1/3.0);
> +  return v;
>  }
>
> and run scale with Reconstruction=Cubic, Sample=Impulse, and Subsample=0,
> it prints
>
> cubic(-2.00) => 0.00
> cubic(-1.00) => 0.06
> cubic(0.00) => 0.89
> cubic(1.00) => 0.06
>
> so the filter generator *does* generate values at [ -2, -1, 0, 1 ]. And as
> mentioned, the sampling code, if given the value 17.5 will convolve with
> the pixels at 15.5, 16.5, 17.5, 18.5, so I'm pretty sure this matrix is
> correct.
>
> (I suspect your changes to the integral() arguments caused it to generate
> different values, so you should check without them included.
>

Looks like you are correct, toggling between this and nearest shows that
the filtering code is reading the arrays this way.


>
> This series is available as a git repository here:
>
>
> https://cgit.freedesktop.org/~sandmann/pixman/log/?h=spitzak-for-master
> )
>
>
> Søren
>
>
___
Pixman mailing list
Pixman@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/pixman


Re: [Pixman] [PATCH 07/14] pixman-image: Added enable-gnuplot config to view filters in gnuplot

2016-04-12 Thread Søren Sandmann
>   1-wide filters - looks triangular, but a 1-wide box would be more
>>accurate
>>
>
> Because you are not plotting the two dummy points at (0,±width/2), a
> 1-wide filter is actually just a single point.
>
> You may be right that leaving the dummy points off the plot may make it
> easier to figure out what is going on.
>

Okay, I will update the comment.

I don't like to make up fake data points, but maybe I should add
[x=-width/2:width/2] to the gnuplot command line.

diff --git a/pixman/rounding.txt b/pixman/rounding.txt
>
>> index b52b084..1c00019 100644
>> --- a/pixman/rounding.txt
>> +++ b/pixman/rounding.txt
>> @@ -160,6 +160,7 @@ which means the contents of the matrix corresponding
>> to (frac) should
>>  contain width samplings of the function, with the first sample at:
>>
>> floor (frac - (width - 1) / 2.0 - e) + 0.5 - frac
>> + = ceil (frac - width / 2.0 - 0.5) + 0.5 - frac
>>
>
> Unfortunately this produces numbers that don't agree with the filter
> generator or filtering code.
>
> For a width==4 filter with n_phases==1, the generator seems to produce
> values at -1, 0, 1, 2, so the first sample is at -1. It also appears the
> filtering sampler is using the same rule, otherwise these filters would
> produce an obvious shift in the image.
>

If you add printf's on top of this series

diff --git a/pixman/pixman-filter.c b/pixman/pixman-filter.c
index 176dfae..4a8743e 100644
--- a/pixman/pixman-filter.c
+++ b/pixman/pixman-filter.c
@@ -129,12 +129,15 @@ general_cubic (double x, double B, double C)
 static double
 cubic_kernel (double x)
 {
+  double v = general_cubic (x, 1/3.0, 1/3.0);
+
+  printf ("cubic(%f) => %f\n", x, v);
 /* This is the Mitchell-Netravali filter.
  *
  * (0.0, 0.5) would give us the Catmull-Rom spline,
  * but that one seems to be indistinguishable from Lanczos2.
  */
-return general_cubic (x, 1/3.0, 1/3.0);
+  return v;
 }

and run scale with Reconstruction=Cubic, Sample=Impulse, and Subsample=0,
it prints

cubic(-2.00) => 0.00
cubic(-1.00) => 0.06
cubic(0.00) => 0.89
cubic(1.00) => 0.06

so the filter generator *does* generate values at [ -2, -1, 0, 1 ]. And as
mentioned, the sampling code, if given the value 17.5 will convolve with
the pixels at 15.5, 16.5, 17.5, 18.5, so I'm pretty sure this matrix is
correct.

(I suspect your changes to the integral() arguments caused it to generate
different values, so you should check without them included.

This series is available as a git repository here:

https://cgit.freedesktop.org/~sandmann/pixman/log/?h=spitzak-for-master
)


Søren
___
Pixman mailing list
Pixman@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/pixman


Re: [Pixman] [PATCH 07/14] pixman-image: Added enable-gnuplot config to view filters in gnuplot

2016-04-12 Thread Bill Spitzak
On Mon, Apr 11, 2016 at 7:36 PM, Søren Sandmann Pedersen <
soren.sandm...@gmail.com> wrote:

> From: Bill Spitzak 
>
> If enable-gnuplot is configured, then you can pipe the output of a
> pixman-using program to gnuplot and get a continuously-updated plot of
> the horizontal filter. This works well with demos/scale to test the
> filter generation.
>
> The plot is all the different subposition filters shuffled
> together. This is misleading in a few cases:
>
>   IMPULSE.BOX - goes up and down as the subfilters have different
> numbers of non-zero samples
>
>   IMPULSE.TRIANGLE - somewhat crooked for the same reason
>
>   1-wide filters - looks triangular, but a 1-wide box would be more
>accurate
>

Because you are not plotting the two dummy points at (0,±width/2), a 1-wide
filter is actually just a single point.

You may be right that leaving the dummy points off the plot may make it
easier to figure out what is going on.


> Changes by Søren: Rewrote the pixman-filter.c part to
>  - make it generate correct coordinates
>  - add a comment on how coordinates are generated
>  - in rounding.txt, add a ceil() variant of the first-sample
>formula
>  - make the gnuplot output slightly prettier
>
> v7: First time this ability was included
>
> v8: Use config option
> Moved code to the filter generator
> Modified scale demo to not call filter generator a second time.
>
> v10: Only print if successful generation of plots
>  Use #ifdef, not #if
>
> v11: small whitespace fixes
>
> Signed-off-by: Bill Spitzak 
> Signed-off-by: Søren Sandmann 
> ---
>  configure.ac   |  13 ++
>  pixman/pixman-filter.c | 115
> +
>  pixman/rounding.txt|   1 +
>  3 files changed, 129 insertions(+)
>
> diff --git a/configure.ac b/configure.ac
> index 6b2134e..e833e45 100644
> --- a/configure.ac
> +++ b/configure.ac
> @@ -834,6 +834,19 @@ fi
>  AC_SUBST(PIXMAN_TIMERS)
>
>  dnl ===
> +dnl gnuplot
> +
> +AC_ARG_ENABLE(gnuplot,
> +   [AC_HELP_STRING([--enable-gnuplot],
> +   [enable output of filters that can be piped to gnuplot
> [default=no]])],
> +   [enable_gnuplot=$enableval], [enable_gnuplot=no])
> +
> +if test $enable_gnuplot = yes ; then
> +   AC_DEFINE(PIXMAN_GNUPLOT, 1, [enable output that can be piped to
> gnuplot])
> +fi
> +AC_SUBST(PIXMAN_GNUPLOT)
> +
> +dnl ===
>  dnl GTK+
>
>  AC_ARG_ENABLE(gtk,
> diff --git a/pixman/pixman-filter.c b/pixman/pixman-filter.c
> index b2bf53f..af46a43 100644
> --- a/pixman/pixman-filter.c
> +++ b/pixman/pixman-filter.c
> @@ -297,6 +297,117 @@ create_1d_filter (int *width,
>  return params;
>  }
>
> +#ifdef PIXMAN_GNUPLOT
> +
> +/* If enable-gnuplot is configured, then you can pipe the output of a
> + * pixman-using program to gnuplot and get a continuously-updated plot
> + * of the horizontal filter. This works well with demos/scale to test
> + * the filter generation.
> + *
> + * The plot is all the different subposition filters shuffled
> + * together. This is misleading in a few cases:
> + *
> + *  IMPULSE.BOX - goes up and down as the subfilters have different
> + *   numbers of non-zero samples
> + *  IMPULSE.TRIANGLE - somewhat crooked for the same reason
> + *  1-wide filters - looks triangular, but a 1-wide box would be more
> + *  accurate
> + */
> +static void
> +gnuplot_filter (int width, int n_phases, const pixman_fixed_t* p)
> +{
> +double step;
> +int i, j;
> +int first;
> +
> +step = 1.0 / n_phases;
> +
> +printf ("set style line 1 lc rgb '#0060ad' lt 1 lw 0.5 pt 7 pi 1 ps
> 0.5\n");
> +printf ("plot '-' with linespoints ls 1\n");
> +
> +/* The position of the first sample of the phase corresponding to
> + * frac is given by:
> + *
> + * ceil (frac - width / 2.0 - 0.5) + 0.5 - frac
> + *
> + * We have to find the frac that minimizes this expression.
> + *
> + * For odd widths, we have
> + *
> + * ceil (frac - width / 2.0 - 0.5) + 0.5 - frac
> + *   = ceil (frac) + K - frac
> + *   = 1 + K - frac
> + *
> + * for some K, so this is minimized when frac is maximized and
> + * strictly growing with frac. So for odd widths, we can simply
> + * start at the last phase and go backwards.
> + *
> + * For even widths, we have
> + *
> + * ceil (frac - width / 2.0 - 0.5) + 0.5 - frac
> + *   = ceil (frac - 0.5) + K - frac
> + *
> + * The graph for this function (ignoring K) looks like this:
> + *
> + *0.5
> + *   ||\
> + *   || \
> + *   ||  \
> + * 0 ||   \
> + *   |\   |
> + *   | \  |
> + *   |  \ |
> + *  -0.5 |   \|
> + *   

Re: [Pixman] [PATCH 03/14] More general BILINEAR=>NEAREST reduction

2016-04-12 Thread Bill Spitzak

Only minor comments on the large nearest patch at the bottom

On 04/11/2016 07:36 PM, Søren Sandmann Pedersen wrote:

Generalize and simplify the code that reduces BILINEAR to NEAREST so
that the reduction happens for all affine transformations where
t00...t12 are integers and (t00 + t01) and (t10 + t11) are both
odd. This is a sufficient condition for the resulting transformed
coordinates to be exactly at the center of a pixel so that BILINEAR
becomes identical to NEAREST.

V2: Address some comments by Bill Spitzak

Signed-off-by: Søren Sandmann 
---
  pixman/pixman-image.c | 66 +--
  1 file changed, 38 insertions(+), 28 deletions(-)

diff --git a/pixman/pixman-image.c b/pixman/pixman-image.c
index 1ff1a49..681864e 100644
--- a/pixman/pixman-image.c
+++ b/pixman/pixman-image.c
@@ -335,37 +335,47 @@ compute_image_info (pixman_image_t *image)
{
flags |= FAST_PATH_NEAREST_FILTER;
}
-   else if (
-   /* affine and integer translation components in matrix ... */
-   ((flags & FAST_PATH_AFFINE_TRANSFORM) &&
-!pixman_fixed_frac (image->common.transform->matrix[0][2] |
-image->common.transform->matrix[1][2])) &&
-   (
-   /* ... combined with a simple rotation */
-   (flags & (FAST_PATH_ROTATE_90_TRANSFORM |
- FAST_PATH_ROTATE_180_TRANSFORM |
- FAST_PATH_ROTATE_270_TRANSFORM)) ||
-   /* ... or combined with a simple non-rotated translation */
-   (image->common.transform->matrix[0][0] == pixman_fixed_1 &&
-image->common.transform->matrix[1][1] == pixman_fixed_1 &&
-image->common.transform->matrix[0][1] == 0 &&
-image->common.transform->matrix[1][0] == 0)
-   )
-   )
+   else if (flags & FAST_PATH_AFFINE_TRANSFORM)
{
-   /* FIXME: there are some affine-test failures, showing that
-* handling of BILINEAR and NEAREST filter is not quite
-* equivalent when getting close to 32K for the translation
-* components of the matrix. That's likely some bug, but for
-* now just skip BILINEAR->NEAREST optimization in this case.
+   /* Suppose the transform is
+*
+*[ t00, t01, t02 ]
+*[ t10, t11, t12 ]
+*[   0,   0,   1 ]
+*
+* and the destination coordinates are (n + 0.5, m + 0.5). Then
+* the transformed x coordinate is:
+*
+* tx = t00 * (n + 0.5) + t01 * (m + 0.5) + t02
+*= t00 * n + t01 * m + t02 + (t00 + t01) * 0.5
+*
+* which implies that if t00, t01 and t02 are all integers
+* and (t00 + t01) is odd, then tx will be an integer plus 0.5,
+* which means a BILINEAR filter will reduce to NEAREST. The same
+* applies in the y direction
 */
-   pixman_fixed_t magic_limit = pixman_int_to_fixed (3);
-   if (image->common.transform->matrix[0][2] <= magic_limit  &&
-   image->common.transform->matrix[1][2] <= magic_limit  &&
-   image->common.transform->matrix[0][2] >= -magic_limit &&
-   image->common.transform->matrix[1][2] >= -magic_limit)
+   pixman_fixed_t (*t)[3] = image->common.transform->matrix;
+
+   if ((pixman_fixed_frac (
+t[0][0] | t[0][1] | t[0][2] |
+t[1][0] | t[1][1] | t[1][2]) == 0) &&
+   (pixman_fixed_to_int (
+   (t[0][0] + t[0][1]) & (t[1][0] + t[1][1])) % 2) == 1)
{
-   flags |= FAST_PATH_NEAREST_FILTER;
+   /* FIXME: there are some affine-test failures, showing that
+* handling of BILINEAR and NEAREST filter is not quite
+* equivalent when getting close to 32K for the translation
+* components of the matrix. That's likely some bug, but for
+* now just skip BILINEAR->NEAREST optimization in this case.
+*/


May be a good idea to point out that the bug is (probably) in BILINEAR, 
not in NEAREST. Also you think this may have been fixed so this could be 
removed, but that would be a different patch.



+   pixman_fixed_t magic_limit = pixman_int_to_fixed (3);
+   if (image->common.transform->matrix[0][2] <= magic_limit  &&
+   image->common.transform->matrix[1][2] <= magic_limit  &&
+   image->common.transform->matrix[0][2] >= -magic_limit &&
+   image->common.transform->matrix[1][2] >= -magic_limit)


I would change these to use 't'.


+   {
+   flags |= FAST_PATH_NEAREST_FILTER;
+   }
}
}
   

Re: [Pixman] [PATCH 02/14] Add new test of filter reduction from BILINEAR to NEAREST

2016-04-12 Thread Bill Spitzak

Reviewed-by: Bill Spitzak 

On 04/11/2016 07:36 PM, Søren Sandmann Pedersen wrote:

This new test tests a bunch of bilinear downscalings, where many have
a transformation such that the BILINEAR filter can be reduced to
NEAREST (and many don't).

A CRC32 is computed for all the resulting images and compared to a
known-good value for both 4-bit and 7-bit interpolation.

V2: Remove leftover comment, some minor formatting fixes, use a
timestamp as the PRNG seed.

Signed-off-by: Søren Sandmann 
---
  test/Makefile.sources|   1 +
  test/filter-reduction-test.c | 112 +++
  2 files changed, 113 insertions(+)
  create mode 100644 test/filter-reduction-test.c

diff --git a/test/Makefile.sources b/test/Makefile.sources
index 5d55e67..0a56231 100644
--- a/test/Makefile.sources
+++ b/test/Makefile.sources
@@ -21,6 +21,7 @@ TESTPROGRAMS =  \
gradient-crash-test   \
pixel-test\
matrix-test   \
+   filter-reduction-test \
composite-traps-test  \
region-contains-test  \
glyph-test\
diff --git a/test/filter-reduction-test.c b/test/filter-reduction-test.c
new file mode 100644
index 000..705fa4b
--- /dev/null
+++ b/test/filter-reduction-test.c
@@ -0,0 +1,112 @@
+#include 
+#include 
+#include "utils.h"
+
+static const pixman_fixed_t entries[] =
+{
+pixman_double_to_fixed (-1.0),
+pixman_double_to_fixed (-0.5),
+pixman_double_to_fixed (-1/3.0),
+pixman_double_to_fixed (0.0),
+pixman_double_to_fixed (0.5),
+pixman_double_to_fixed (1.0),
+pixman_double_to_fixed (1.5),
+pixman_double_to_fixed (2.0),
+pixman_double_to_fixed (3.0),
+};
+
+#define SIZE 12
+
+static uint32_t
+test_scale (const pixman_transform_t *xform, uint32_t crc)
+{
+uint32_t *srcbuf, *dstbuf;
+pixman_image_t *src, *dest;
+
+srcbuf = malloc (SIZE * SIZE * 4);
+prng_randmemset (srcbuf, SIZE * SIZE * 4, 0);
+src = pixman_image_create_bits (
+   PIXMAN_a8r8g8b8, SIZE, SIZE, srcbuf, SIZE * 4);
+
+dstbuf = malloc (SIZE * SIZE * 4);
+prng_randmemset (dstbuf, SIZE * SIZE * 4, 0);
+dest = pixman_image_create_bits (
+   PIXMAN_a8r8g8b8, SIZE, SIZE, dstbuf, SIZE * 4);
+
+pixman_image_set_transform (src, xform);
+pixman_image_set_repeat (src, PIXMAN_REPEAT_NORMAL);
+pixman_image_set_filter (src, PIXMAN_FILTER_BILINEAR, NULL, 0);
+
+image_endian_swap (src);
+image_endian_swap (dest);
+
+pixman_image_composite (PIXMAN_OP_SRC,
+   src, NULL, dest,
+   0, 0, 0, 0, 0, 0,
+   SIZE, SIZE);
+
+crc = compute_crc32_for_image (crc, dest);
+
+pixman_image_unref (src);
+pixman_image_unref (dest);
+
+free (srcbuf);
+free (dstbuf);
+
+return crc;
+}
+
+#if BILINEAR_INTERPOLATION_BITS == 7
+#define CHECKSUM 0x02169677
+#elif BILINEAR_INTERPOLATION_BITS == 4
+#define CHECKSUM 0xE44B29AC
+#else
+#define CHECKSUM 0x
+#endif
+
+int
+main (int argc, const char *argv[])
+{
+const pixman_fixed_t *end = entries + ARRAY_LENGTH (entries);
+const pixman_fixed_t *t0, *t1, *t2, *t3, *t4, *t5;
+uint32_t crc = 0;
+
+prng_srand (0x56EA1DBD);
+
+for (t0 = entries; t0 < end; ++t0)
+{
+   for (t1 = entries; t1 < end; ++t1)
+   {
+   for (t2 = entries; t2 < end; ++t2)
+   {
+   for (t3 = entries; t3 < end; ++t3)
+   {
+   for (t4 = entries; t4 < end; ++t4)
+   {
+   for (t5 = entries; t5 < end; ++t5)
+   {
+   pixman_transform_t xform = {
+   { { *t0, *t1, *t2 },
+ { *t3, *t4, *t5 },
+ { 0, 0, pixman_fixed_1 } }
+   };
+
+   crc = test_scale (, crc);
+   }
+   }
+   }
+   }
+   }
+}
+
+if (crc != CHECKSUM)
+{
+   printf ("filter-reduction-test failed! (checksum=0x%08X, expected 
0x%08X)\n", crc, CHECKSUM);
+   return 1;
+}
+else
+{
+   printf ("filter-reduction-test passed (checksum=0x%08X)\n", crc);
+   return 0;
+}
+}



___
Pixman mailing list
Pixman@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/pixman


Re: [Pixman] [PATCH 01/14] pixman-fast-path.c: Pick NEAREST affine fast paths before BILINEAR ones

2016-04-12 Thread Bill Spitzak
I can confirm this fixes the problem and allows multiple fast path flags 
to be set.


Reviewed-by: Bill Spitzak 

On 04/11/2016 07:36 PM, Søren Sandmann Pedersen wrote:

When a BILINEAR filter is reduced to NEAREST, it is possible for both
types of fast paths to run; in this case, the NEAREST ones should be
preferred as that is the simpler filter.

Signed-off-by: Soren Sandmann 
---
  pixman/pixman-fast-path.c | 4 ++--
  1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/pixman/pixman-fast-path.c b/pixman/pixman-fast-path.c
index 53d4a1f..b4daa26 100644
--- a/pixman/pixman-fast-path.c
+++ b/pixman/pixman-fast-path.c
@@ -3258,9 +3258,9 @@ static const pixman_iter_info_t fast_iters[] =
  },

  #define AFFINE_FAST_PATHS(name, format, repeat)   
\
-SEPARABLE_CONVOLUTION_AFFINE_FAST_PATH(name, format, repeat)   \
+NEAREST_AFFINE_FAST_PATH(name, format, repeat) \
  BILINEAR_AFFINE_FAST_PATH(name, format, repeat)   \
-NEAREST_AFFINE_FAST_PATH(name, format, repeat)
+SEPARABLE_CONVOLUTION_AFFINE_FAST_PATH(name, format, repeat)

  AFFINE_FAST_PATHS (pad_a8r8g8b8, a8r8g8b8, PAD)
  AFFINE_FAST_PATHS (none_a8r8g8b8, a8r8g8b8, NONE)



___
Pixman mailing list
Pixman@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/pixman