gfx/cairo/libpixman/src/pixman-combine32.h

Wed, 31 Dec 2014 06:09:35 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Wed, 31 Dec 2014 06:09:35 +0100
changeset 0
6474c204b198
permissions
-rw-r--r--

Cloned upstream origin tor-browser at tor-browser-31.3.0esr-4.5-1-build1
revision ID fc1c9ff7c1b2defdbc039f12214767608f46423f for hacking purpose.

     1 #define COMPONENT_SIZE 8
     2 #define MASK 0xff
     3 #define ONE_HALF 0x80
     5 #define A_SHIFT 8 * 3
     6 #define R_SHIFT 8 * 2
     7 #define G_SHIFT 8
     8 #define A_MASK 0xff000000
     9 #define R_MASK 0xff0000
    10 #define G_MASK 0xff00
    12 #define RB_MASK 0xff00ff
    13 #define AG_MASK 0xff00ff00
    14 #define RB_ONE_HALF 0x800080
    15 #define RB_MASK_PLUS_ONE 0x10000100
    17 #define ALPHA_8(x) ((x) >> A_SHIFT)
    18 #define RED_8(x) (((x) >> R_SHIFT) & MASK)
    19 #define GREEN_8(x) (((x) >> G_SHIFT) & MASK)
    20 #define BLUE_8(x) ((x) & MASK)
    22 /*
    23  * ARMv6 has UQADD8 instruction, which implements unsigned saturated
    24  * addition for 8-bit values packed in 32-bit registers. It is very useful
    25  * for UN8x4_ADD_UN8x4, UN8_rb_ADD_UN8_rb and ADD_UN8 macros (which would
    26  * otherwise need a lot of arithmetic operations to simulate this operation).
    27  * Since most of the major ARM linux distros are built for ARMv7, we are
    28  * much less dependent on runtime CPU detection and can get practical
    29  * benefits from conditional compilation here for a lot of users.
    30  */
    32 #if defined(USE_GCC_INLINE_ASM) && defined(__arm__) && \
    33     !defined(__aarch64__) && (!defined(__thumb__) || defined(__thumb2__))
    34 #if defined(__ARM_ARCH_6__)   || defined(__ARM_ARCH_6J__)  || \
    35     defined(__ARM_ARCH_6K__)  || defined(__ARM_ARCH_6Z__)  || \
    36     defined(__ARM_ARCH_6ZK__) || defined(__ARM_ARCH_6T2__) || \
    37     defined(__ARM_ARCH_6M__)  || defined(__ARM_ARCH_7__)   || \
    38     defined(__ARM_ARCH_7A__)  || defined(__ARM_ARCH_7R__)  || \
    39     defined(__ARM_ARCH_7M__)  || defined(__ARM_ARCH_7EM__)
    41 static force_inline uint32_t
    42 un8x4_add_un8x4 (uint32_t x, uint32_t y)
    43 {
    44     uint32_t t;
    45     asm ("uqadd8 %0, %1, %2" : "=r" (t) : "%r" (x), "r" (y));
    46     return t;
    47 }
    49 #define UN8x4_ADD_UN8x4(x, y) \
    50     ((x) = un8x4_add_un8x4 ((x), (y)))
    52 #define UN8_rb_ADD_UN8_rb(x, y, t) \
    53     ((t) = un8x4_add_un8x4 ((x), (y)), (x) = (t))
    55 #define ADD_UN8(x, y, t) \
    56     ((t) = (x), un8x4_add_un8x4 ((t), (y)))
    58 #endif
    59 #endif
    61 /*****************************************************************************/
    63 /*
    64  * Helper macros.
    65  */
    67 #define MUL_UN8(a, b, t)						\
    68     ((t) = (a) * (uint16_t)(b) + ONE_HALF, ((((t) >> G_SHIFT ) + (t) ) >> G_SHIFT ))
    70 #define DIV_UN8(a, b)							\
    71     (((uint16_t) (a) * MASK + ((b) / 2)) / (b))
    73 #ifndef ADD_UN8
    74 #define ADD_UN8(x, y, t)				     \
    75     ((t) = (x) + (y),					     \
    76      (uint32_t) (uint8_t) ((t) | (0 - ((t) >> G_SHIFT))))
    77 #endif
    79 #define DIV_ONE_UN8(x)							\
    80     (((x) + ONE_HALF + (((x) + ONE_HALF) >> G_SHIFT)) >> G_SHIFT)
    82 /*
    83  * The methods below use some tricks to be able to do two color
    84  * components at the same time.
    85  */
    87 /*
    88  * x_rb = (x_rb * a) / 255
    89  */
    90 #define UN8_rb_MUL_UN8(x, a, t)						\
    91     do									\
    92     {									\
    93 	t  = ((x) & RB_MASK) * (a);					\
    94 	t += RB_ONE_HALF;						\
    95 	x = (t + ((t >> G_SHIFT) & RB_MASK)) >> G_SHIFT;		\
    96 	x &= RB_MASK;							\
    97     } while (0)
    99 /*
   100  * x_rb = min (x_rb + y_rb, 255)
   101  */
   102 #ifndef UN8_rb_ADD_UN8_rb
   103 #define UN8_rb_ADD_UN8_rb(x, y, t)					\
   104     do									\
   105     {									\
   106 	t = ((x) + (y));						\
   107 	t |= RB_MASK_PLUS_ONE - ((t >> G_SHIFT) & RB_MASK);		\
   108 	x = (t & RB_MASK);						\
   109     } while (0)
   110 #endif
   112 /*
   113  * x_rb = (x_rb * a_rb) / 255
   114  */
   115 #define UN8_rb_MUL_UN8_rb(x, a, t)					\
   116     do									\
   117     {									\
   118 	t  = (x & MASK) * (a & MASK);					\
   119 	t |= (x & R_MASK) * ((a >> R_SHIFT) & MASK);			\
   120 	t += RB_ONE_HALF;						\
   121 	t = (t + ((t >> G_SHIFT) & RB_MASK)) >> G_SHIFT;		\
   122 	x = t & RB_MASK;						\
   123     } while (0)
   125 /*
   126  * x_c = (x_c * a) / 255
   127  */
   128 #define UN8x4_MUL_UN8(x, a)						\
   129     do									\
   130     {									\
   131 	uint32_t r1__, r2__, t__;					\
   132 									\
   133 	r1__ = (x);							\
   134 	UN8_rb_MUL_UN8 (r1__, (a), t__);				\
   135 									\
   136 	r2__ = (x) >> G_SHIFT;						\
   137 	UN8_rb_MUL_UN8 (r2__, (a), t__);				\
   138 									\
   139 	(x) = r1__ | (r2__ << G_SHIFT);					\
   140     } while (0)
   142 /*
   143  * x_c = (x_c * a) / 255 + y_c
   144  */
   145 #define UN8x4_MUL_UN8_ADD_UN8x4(x, a, y)				\
   146     do									\
   147     {									\
   148 	uint32_t r1__, r2__, r3__, t__;					\
   149 									\
   150 	r1__ = (x);							\
   151 	r2__ = (y) & RB_MASK;						\
   152 	UN8_rb_MUL_UN8 (r1__, (a), t__);				\
   153 	UN8_rb_ADD_UN8_rb (r1__, r2__, t__);				\
   154 									\
   155 	r2__ = (x) >> G_SHIFT;						\
   156 	r3__ = ((y) >> G_SHIFT) & RB_MASK;				\
   157 	UN8_rb_MUL_UN8 (r2__, (a), t__);				\
   158 	UN8_rb_ADD_UN8_rb (r2__, r3__, t__);				\
   159 									\
   160 	(x) = r1__ | (r2__ << G_SHIFT);					\
   161     } while (0)
   163 /*
   164  * x_c = (x_c * a + y_c * b) / 255
   165  */
   166 #define UN8x4_MUL_UN8_ADD_UN8x4_MUL_UN8(x, a, y, b)			\
   167     do									\
   168     {									\
   169 	uint32_t r1__, r2__, r3__, t__;					\
   170 									\
   171 	r1__ = (x);							\
   172 	r2__ = (y);							\
   173 	UN8_rb_MUL_UN8 (r1__, (a), t__);				\
   174 	UN8_rb_MUL_UN8 (r2__, (b), t__);				\
   175 	UN8_rb_ADD_UN8_rb (r1__, r2__, t__);				\
   176 									\
   177 	r2__ = ((x) >> G_SHIFT);					\
   178 	r3__ = ((y) >> G_SHIFT);					\
   179 	UN8_rb_MUL_UN8 (r2__, (a), t__);				\
   180 	UN8_rb_MUL_UN8 (r3__, (b), t__);				\
   181 	UN8_rb_ADD_UN8_rb (r2__, r3__, t__);				\
   182 									\
   183 	(x) = r1__ | (r2__ << G_SHIFT);					\
   184     } while (0)
   186 /*
   187  * x_c = (x_c * a_c) / 255
   188  */
   189 #define UN8x4_MUL_UN8x4(x, a)						\
   190     do									\
   191     {									\
   192 	uint32_t r1__, r2__, r3__, t__;					\
   193 									\
   194 	r1__ = (x);							\
   195 	r2__ = (a);							\
   196 	UN8_rb_MUL_UN8_rb (r1__, r2__, t__);				\
   197 									\
   198 	r2__ = (x) >> G_SHIFT;						\
   199 	r3__ = (a) >> G_SHIFT;						\
   200 	UN8_rb_MUL_UN8_rb (r2__, r3__, t__);				\
   201 									\
   202 	(x) = r1__ | (r2__ << G_SHIFT);					\
   203     } while (0)
   205 /*
   206  * x_c = (x_c * a_c) / 255 + y_c
   207  */
   208 #define UN8x4_MUL_UN8x4_ADD_UN8x4(x, a, y)				\
   209     do									\
   210     {									\
   211 	uint32_t r1__, r2__, r3__, t__;					\
   212 									\
   213 	r1__ = (x);							\
   214 	r2__ = (a);							\
   215 	UN8_rb_MUL_UN8_rb (r1__, r2__, t__);				\
   216 	r2__ = (y) & RB_MASK;						\
   217 	UN8_rb_ADD_UN8_rb (r1__, r2__, t__);				\
   218 									\
   219 	r2__ = ((x) >> G_SHIFT);					\
   220 	r3__ = ((a) >> G_SHIFT);					\
   221 	UN8_rb_MUL_UN8_rb (r2__, r3__, t__);				\
   222 	r3__ = ((y) >> G_SHIFT) & RB_MASK;				\
   223 	UN8_rb_ADD_UN8_rb (r2__, r3__, t__);				\
   224 									\
   225 	(x) = r1__ | (r2__ << G_SHIFT);					\
   226     } while (0)
   228 /*
   229  * x_c = (x_c * a_c + y_c * b) / 255
   230  */
   231 #define UN8x4_MUL_UN8x4_ADD_UN8x4_MUL_UN8(x, a, y, b)			\
   232     do									\
   233     {									\
   234 	uint32_t r1__, r2__, r3__, t__;					\
   235 									\
   236 	r1__ = (x);							\
   237 	r2__ = (a);							\
   238 	UN8_rb_MUL_UN8_rb (r1__, r2__, t__);				\
   239 	r2__ = (y);							\
   240 	UN8_rb_MUL_UN8 (r2__, (b), t__);				\
   241 	UN8_rb_ADD_UN8_rb (r1__, r2__, t__);				\
   242 									\
   243 	r2__ = (x) >> G_SHIFT;						\
   244 	r3__ = (a) >> G_SHIFT;						\
   245 	UN8_rb_MUL_UN8_rb (r2__, r3__, t__);				\
   246 	r3__ = (y) >> G_SHIFT;						\
   247 	UN8_rb_MUL_UN8 (r3__, (b), t__);				\
   248 	UN8_rb_ADD_UN8_rb (r2__, r3__, t__);				\
   249 									\
   250 	x = r1__ | (r2__ << G_SHIFT);					\
   251     } while (0)
   253 /*
   254   x_c = min(x_c + y_c, 255)
   255 */
   256 #ifndef UN8x4_ADD_UN8x4
   257 #define UN8x4_ADD_UN8x4(x, y)						\
   258     do									\
   259     {									\
   260 	uint32_t r1__, r2__, r3__, t__;					\
   261 									\
   262 	r1__ = (x) & RB_MASK;						\
   263 	r2__ = (y) & RB_MASK;						\
   264 	UN8_rb_ADD_UN8_rb (r1__, r2__, t__);				\
   265 									\
   266 	r2__ = ((x) >> G_SHIFT) & RB_MASK;				\
   267 	r3__ = ((y) >> G_SHIFT) & RB_MASK;				\
   268 	UN8_rb_ADD_UN8_rb (r2__, r3__, t__);				\
   269 									\
   270 	x = r1__ | (r2__ << G_SHIFT);					\
   271     } while (0)
   272 #endif

mercurial