1 /*
2 * Copyright 2011 Google Inc.
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
6 */
7
8 #include "SkBlitRow.h"
9 #include "SkBlitMask.h"
10 #include "SkColorPriv.h"
11 #include "SkOpts.h"
12 #include "SkUtils.h"
13
14 #define UNROLL
15
S32_Opaque_BlitRow32(SkPMColor * SK_RESTRICT dst,const SkPMColor * SK_RESTRICT src,int count,U8CPU alpha)16 static void S32_Opaque_BlitRow32(SkPMColor* SK_RESTRICT dst,
17 const SkPMColor* SK_RESTRICT src,
18 int count, U8CPU alpha) {
19 SkASSERT(255 == alpha);
20 memcpy(dst, src, count * 4);
21 }
22
S32_Blend_BlitRow32(SkPMColor * SK_RESTRICT dst,const SkPMColor * SK_RESTRICT src,int count,U8CPU alpha)23 static void S32_Blend_BlitRow32(SkPMColor* SK_RESTRICT dst,
24 const SkPMColor* SK_RESTRICT src,
25 int count, U8CPU alpha) {
26 SkASSERT(alpha <= 255);
27 if (count > 0) {
28 unsigned src_scale = SkAlpha255To256(alpha);
29
30 #ifdef UNROLL
31 if (count & 1) {
32 *dst = SkPMLerp(*src, *dst, src_scale);
33 src += 1;
34 dst += 1;
35 count -= 1;
36 }
37
38 const SkPMColor* SK_RESTRICT srcEnd = src + count;
39 while (src != srcEnd) {
40 *dst = SkPMLerp(*src, *dst, src_scale);
41 src += 1;
42 dst += 1;
43 *dst = SkPMLerp(*src, *dst, src_scale);
44 src += 1;
45 dst += 1;
46 }
47 #else
48 do {
49 *dst = SkPMLerp(*src, *dst, src_scale);
50 src += 1;
51 dst += 1;
52 } while (--count > 0);
53 #endif
54 }
55 }
56
S32A_Blend_BlitRow32(SkPMColor * SK_RESTRICT dst,const SkPMColor * SK_RESTRICT src,int count,U8CPU alpha)57 static void S32A_Blend_BlitRow32(SkPMColor* SK_RESTRICT dst,
58 const SkPMColor* SK_RESTRICT src,
59 int count, U8CPU alpha) {
60 SkASSERT(alpha <= 255);
61 if (count > 0) {
62 #ifdef UNROLL
63 if (count & 1) {
64 *dst = SkBlendARGB32(*(src++), *dst, alpha);
65 dst += 1;
66 count -= 1;
67 }
68
69 const SkPMColor* SK_RESTRICT srcEnd = src + count;
70 while (src != srcEnd) {
71 *dst = SkBlendARGB32(*(src++), *dst, alpha);
72 dst += 1;
73 *dst = SkBlendARGB32(*(src++), *dst, alpha);
74 dst += 1;
75 }
76 #else
77 do {
78 *dst = SkBlendARGB32(*src, *dst, alpha);
79 src += 1;
80 dst += 1;
81 } while (--count > 0);
82 #endif
83 }
84 }
85
86 ///////////////////////////////////////////////////////////////////////////////
87
88 static const SkBlitRow::Proc32 gDefault_Procs32[] = {
89 S32_Opaque_BlitRow32,
90 S32_Blend_BlitRow32,
91 nullptr,
92 S32A_Blend_BlitRow32
93 };
94
Factory32(unsigned flags)95 SkBlitRow::Proc32 SkBlitRow::Factory32(unsigned flags) {
96 SkASSERT(flags < SK_ARRAY_COUNT(gDefault_Procs32));
97 // just so we don't crash
98 flags &= kFlags32_Mask;
99
100 if (flags == 2) {
101 // S32A_Opaque_BlitRow32 has been ported to SkOpts, but not the others yet.
102 return SkOpts::blit_row_s32a_opaque;
103 }
104
105 SkBlitRow::Proc32 proc = PlatformProcs32(flags);
106 if (nullptr == proc) {
107 proc = gDefault_Procs32[flags];
108 }
109 SkASSERT(proc);
110 return proc;
111 }
112
Color32(SkPMColor dst[],const SkPMColor src[],int count,SkPMColor color)113 void SkBlitRow::Color32(SkPMColor dst[], const SkPMColor src[], int count, SkPMColor color) {
114 switch (SkGetPackedA32(color)) {
115 case 0: memmove(dst, src, count * sizeof(SkPMColor)); return;
116 case 255: sk_memset32(dst, color, count); return;
117 }
118 return SkOpts::blit_row_color32(dst, src, count, color);
119 }
120