Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(536)

Side by Side Diff: media/base/simd/convert_yuv_to_rgb_ssse3.inc

Issue 7003082: Implements RGB to YV12 conversion in YASM. (Closed) Base URL: svn://chrome-svn/chrome/trunk/src/
Patch Set: '' Created 9 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 ; Copyright (c) 2011 The Chromium Authors. All rights reserved.
2 ; Use of this source code is governed by a BSD-style license that can be
3 ; found in the LICENSE file.
4
5 ;
6 ; void SYMBOL(const uint8* y,
7 ; const uint8* u,
8 ; const uint8* v,
9 ; uint8* argb,
10 ; int width);
11 ;
12 ; Converts a row of YUV (4:1:1) pixels to the ARGB (RGB) colorspace. This
13 ; function reads YUV pixels from right to left, convert their colorspace to ARGB
14 ; (RGB), and write the converted pixels to the output buffers. The following
15 ; code snippet represents the rough structure of this fucntion.
16 ;
17 ; if (width & 1) {
18 ; --width;
19 ; convert_one_pixel(y, u, v, argb, width);
20 ; }
21 ; if (width & 2) {
22 ; width -= 2;
23 ; convert_two_pixels(y, u, v, argb, width);
24 ; }
25 ; while (width) {
26 ; width -= 4;
27 ; convert_four_pixels(y, u, v, argb, width);
28 ; }
29 ;
30 ; This function has pseudo-code snippets to describe its behaviors. For
31 ; simplicity, they use the following notations.
32 ;
33 ; #define Y(n) y[n] - 16
34 ; #define U(n) u[n] - 128
35 ; #define V(n) v[n] - 128
36 ; #define FIX(n) (n * (1 << SHIFT_BITS) * 0.5)
37 ; #define ToByte(n) ((n < 0) ? 0 : (n > 255 ? 255 : n))
38 ;
39 ; union {
40 ; int32 d[4];
41 ; int16 w[8];
42 ; int8 b[16];
43 ; } xmm0, xmm1, xmm2, xmm3, xmm4, xmm5, xmm6, xmm7
44 ;
45 ;
46 global SYMBOL PRIVATE
47 align function_align
48
49 SYMBOL:
50 %assign stack_offset 0
51 PROLOGUE 5, 6, 8, Y, U, V, ARGB, WIDTH, TEMP
52
53 ; Initialize constants used in this function.
54 LOAD_SYM TEMPq, SIMD_ConvertYUVtoARGB_kTable
55 movdqa xmm0, DQWORD [TEMPq + 0]
56 movdqa xmm1, DQWORD [TEMPq + 16]
57 pshufd XMM_CONST_BIAS, xmm0, 01000100B
58 pshufd XMM_CONST_R, xmm0, 11101110B
59 pshufd XMM_CONST_G, xmm1, 01000100B
60 pshufd XMM_CONST_B, xmm1, 11101110B
61
62 .convert_one_pixel:
63 ; Divide the input width by two so it represents the offsets for u[] and v[].
64 ; When the width is odd, We read the rightmost ARGB pixel and convert its
65 ; colorspace to YUV. This code stores one Y pixel, one U pixel, and one V
66 ; pixel.
67 sar WIDTHq, 1
68 jnc .convert_two_pixels
69
70 ; Read one Y pixel, one U pixel, and one V pixel. It packs the pixels into
71 ; xmm0.
72 READ_YUV 1
73
74 ; Calculate r[0].
75 movdqa xmm2, xmm0
76 CALC_R xmm2, xmm3, 1
77 movd TEMPd, xmm2
78
79 ; Calculate g[0].
80 movdqa xmm2, xmm0
81 CALC_G xmm2, xmm3, 1
82
83 ; Calculate b[0].
84 CALC_B xmm0, xmm1, 1
85
86 ; Interleave r[0], g[0], and b[0] to create one ARGB pixel.
87 movd xmm1, TEMPd
88 PACK_ARGB xmm0, xmm2, xmm1
89
90 %if PIXELSIZE == 4
91 movd DWORD [ARGBq + WIDTHq * 4 * 2], xmm0
92 %else
93 MOVq xmm1, WIDTHq
94 lea WIDTHq, [WIDTHq + WIDTHq * 2]
95 movd TEMPd, xmm0
96 mov WORD [ARGBq + WIDTHq * 2], TEMPw
97 sar TEMPw, 16
98 mov BYTE [ARGBq + WIDTHq * 2 + 2], TEMPb
99 MOVq WIDTHq, xmm1
100 %endif
101
102 .convert_two_pixels:
103 ; When the input width is not a multiple of four, we read the rightmost two Y
104 ; pixels, one U pixel, and one V pixel to convert their colorspace to RGB.
105 ; This code stores two RGBA pixels.
106 test WIDTHb, 1
107 jz .convert_four_pixels
108 sub WIDTHq, 2 / 2
109
110 ; Read two Y pixels, one U pixels, and one V pixels to xmm0.
111 READ_YUV 2
112
113 ; Calculate r[0] and r[0].
114 movdqa xmm2, xmm0
115 CALC_R xmm2, xmm3, 1
116 movd TEMPd, xmm2
117
118 ; Calculate g[0].
119 movdqa xmm2, xmm0
120 CALC_G xmm2, xmm3, 1
121
122 ; Calculate b[0].
123 CALC_B xmm0, xmm1, 1
124
125 ; Interleave r[0], g[0], and b[0] to create one ARGB pixel.
126 movd xmm1, TEMPd
127 PACK_ARGB xmm0, xmm2, xmm1
128
129 %if PIXELSIZE == 4
130 movq QWORD [ARGBq + WIDTHq * 4 * 2], xmm0
131 %else
132 MOVq xmm1, WIDTHq
133 lea WIDTHq, [WIDTHq + WIDTHq * 2]
134 movd DWORD [ARGBq + WIDTHq * 2], xmm0
135 psrldq xmm0, 4
136 movd TEMPd, xmm0
137 mov WORD [ARGBq + WIDTHq * 2 + 4], TEMPw
138 MOVq WIDTHq, xmm1
139 %endif
140
141 .convert_four_pixels:
142 ; Read four Y pixels, two U pixels, and two V pixels to convert their
143 ; colorspace to RGB. This code stores four RGBA (or RGB) pixels.
144 test WIDTHq, WIDTHq
145 jz .convert_finish
146
147 %if PIXELSIZE == 4
148 ; Check if the input buffer is aligned to a 16-byte boundary so we can use
149 ; movdqa for writing the ARGB pixels if possible.
150 test ARGBw, 15
151 jnz .convert_four_pixels_unaligned
152
153 .convert_four_pixels_aligned:
154 sub WIDTHq, 4 / 2
155
156 ; Read four Y pixels, two U pixels, and two V pixels to xmm0 and xmm1.
157 READ_YUV 4
158
159 ; Calculate r[0],...,r[3]. It saves the results to TEMP.b[0],...,TEMP.b[3],
160 ; respecitively.
161 movdqa xmm2, xmm0
162 movdqa xmm3, xmm1
163 CALC_R xmm2, xmm3, 4
164 movd TEMPd, xmm2
165
166 ; Calculate g[0],...,g[3]. It saves the results to xmm2.b[0],...,xmm2.b[3],
167 ; respectively.
168 movdqa xmm2, xmm0
169 movdqa xmm3, xmm1
170 CALC_G xmm2, xmm3, 4
171
172 ; Calculate b[0],...,b[3]. It saves the results to xmm0.b[0],...,xmm0.b[3],
173 ; respectively.
174 CALC_B xmm0, xmm1, 4
175
176 ; Interleave r[0],...,r[3], g[0],...,g[3], and b[0],...,b[3] to create four
177 ; ARGB pixels
178 movd xmm1, TEMPd
179 PACK_ARGB xmm0, xmm2, xmm1
180
181 ; Write four ARGB pixels. (We can use movdqa here since we have checked if the
182 ; destination address is aligned.)
183 movdqa DQWORD [ARGBq + WIDTHq * 4 * 2], xmm0
184
185 test WIDTHq, WIDTHq
186 jnz .convert_four_pixels_aligned
187
188 jmp .convert_finish
189 %endif ; PIXELSIZE == 4
190
191 .convert_four_pixels_unaligned:
192 sub WIDTHq, 4 / 2
193
194 ; Read four Y pixels, two U pixels, and two V pixels to xmm0 and xmm1.
195 READ_YUV 4
196
197 ; Calculate r[0],...,r[3]. It saves the results to TEMP.b[0],...,TEMP.b[3],
198 ; respecitively.
199 movdqa xmm2, xmm0
200 movdqa xmm3, xmm1
201 CALC_R xmm2, xmm3, 4
202 movd TEMPd, xmm2
203
204 ; Calculate g[0],...,g[3]. It saves the results to xmm2.b[0],...,xmm2.b[3],
205 ; respectively.
206 movdqa xmm2, xmm0
207 movdqa xmm3, xmm1
208 CALC_G xmm2, xmm3, 4
209
210 ; Calculate b[0],...,b[3]. It saves the results to xmm0.b[0],...,xmm0.b[3],
211 ; respectively.
212 CALC_B xmm0, xmm1, 4
213
214 ; Interleave r[0],...,r[3], g[0],...,g[3], and b[0],...,b[3] to create four
215 ; ARGB pixels
216 movd xmm1, TEMPd
217 PACK_ARGB xmm0, xmm2, xmm1
218
219 %if PIXELSIZE == 4
220 movdqu DQWORD [ARGBq + WIDTHq * 4 * 2], xmm0
221 %else
222 ; Pack four ARGB pixels to four RGB pixels.
223 PACK_RGB xmm0, 12
224 PACK_RGB xmm0, 8
225 PACK_RGB xmm0, 4
226
227 mov TEMPq, WIDTHq
228 lea TEMPq, [TEMPq + TEMPq * 2]
229 movq QWORD [ARGBq + TEMPq * 2], xmm0
230 psrldq xmm0, 8
231 movd DWORD [ARGBq + TEMPq * 2 + 8], xmm0
232 %endif
233
234 test WIDTHq, WIDTHq
235 jnz .convert_four_pixels_unaligned
236
237 .convert_finish:
238 ; Just exit this function since this is a void function.
239 RET
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698