1 // SPDX-License-Identifier: GPL-2.0-only
2 /*
3  * v4l2-tpg-core.c - Test Pattern Generator
4  *
5  * Note: gen_twopix and tpg_gen_text are based on code from vivi.c. See the
6  * vivi.c source for the copyright information of those functions.
7  *
8  * Copyright 2014 Cisco Systems, Inc. and/or its affiliates. All rights reserved.
9  */
10 
11 #include <linux/module.h>
12 #include <media/tpg/v4l2-tpg.h>
13 
14 /* Must remain in sync with enum tpg_pattern */
15 const char * const tpg_pattern_strings[] = {
16 	"75% Colorbar",
17 	"100% Colorbar",
18 	"CSC Colorbar",
19 	"Horizontal 100% Colorbar",
20 	"100% Color Squares",
21 	"100% Black",
22 	"100% White",
23 	"100% Red",
24 	"100% Green",
25 	"100% Blue",
26 	"16x16 Checkers",
27 	"2x2 Checkers",
28 	"1x1 Checkers",
29 	"2x2 Red/Green Checkers",
30 	"1x1 Red/Green Checkers",
31 	"Alternating Hor Lines",
32 	"Alternating Vert Lines",
33 	"One Pixel Wide Cross",
34 	"Two Pixels Wide Cross",
35 	"Ten Pixels Wide Cross",
36 	"Gray Ramp",
37 	"Noise",
38 	NULL
39 };
40 EXPORT_SYMBOL_GPL(tpg_pattern_strings);
41 
42 /* Must remain in sync with enum tpg_aspect */
43 const char * const tpg_aspect_strings[] = {
44 	"Source Width x Height",
45 	"4x3",
46 	"14x9",
47 	"16x9",
48 	"16x9 Anamorphic",
49 	NULL
50 };
51 EXPORT_SYMBOL_GPL(tpg_aspect_strings);
52 
53 /*
54  * Sine table: sin[0] = 127 * sin(-180 degrees)
55  *             sin[128] = 127 * sin(0 degrees)
56  *             sin[256] = 127 * sin(180 degrees)
57  */
58 static const s8 sin[257] = {
59 	   0,   -4,   -7,  -11,  -13,  -18,  -20,  -22,  -26,  -29,  -33,  -35,  -37,  -41,  -43,  -48,
60 	 -50,  -52,  -56,  -58,  -62,  -63,  -65,  -69,  -71,  -75,  -76,  -78,  -82,  -83,  -87,  -88,
61 	 -90,  -93,  -94,  -97,  -99, -101, -103, -104, -107, -108, -110, -111, -112, -114, -115, -117,
62 	-118, -119, -120, -121, -122, -123, -123, -124, -125, -125, -126, -126, -127, -127, -127, -127,
63 	-127, -127, -127, -127, -126, -126, -125, -125, -124, -124, -123, -122, -121, -120, -119, -118,
64 	-117, -116, -114, -113, -111, -110, -109, -107, -105, -103, -101, -100,  -97,  -96,  -93,  -91,
65 	 -90,  -87,  -85,  -82,  -80,  -76,  -75,  -73,  -69,  -67,  -63,  -62,  -60,  -56,  -54,  -50,
66 	 -48,  -46,  -41,  -39,  -35,  -33,  -31,  -26,  -24,  -20,  -18,  -15,  -11,   -9,   -4,   -2,
67 	   0,    2,    4,    9,   11,   15,   18,   20,   24,   26,   31,   33,   35,   39,   41,   46,
68 	  48,   50,   54,   56,   60,   62,   64,   67,   69,   73,   75,   76,   80,   82,   85,   87,
69 	  90,   91,   93,   96,   97,  100,  101,  103,  105,  107,  109,  110,  111,  113,  114,  116,
70 	 117,  118,  119,  120,  121,  122,  123,  124,  124,  125,  125,  126,  126,  127,  127,  127,
71 	 127,  127,  127,  127,  127,  126,  126,  125,  125,  124,  123,  123,  122,  121,  120,  119,
72 	 118,  117,  115,  114,  112,  111,  110,  108,  107,  104,  103,  101,   99,   97,   94,   93,
73 	  90,   88,   87,   83,   82,   78,   76,   75,   71,   69,   65,   64,   62,   58,   56,   52,
74 	  50,   48,   43,   41,   37,   35,   33,   29,   26,   22,   20,   18,   13,   11,    7,    4,
75 	   0,
76 };
77 
78 #define cos(idx) sin[((idx) + 64) % sizeof(sin)]
79 
80 /* Global font descriptor */
81 static const u8 *font8x16;
82 
83 void tpg_set_font(const u8 *f)
84 {
85 	font8x16 = f;
86 }
87 EXPORT_SYMBOL_GPL(tpg_set_font);
88 
89 void tpg_init(struct tpg_data *tpg, unsigned w, unsigned h)
90 {
91 	memset(tpg, 0, sizeof(*tpg));
92 	tpg->scaled_width = tpg->src_width = w;
93 	tpg->src_height = tpg->buf_height = h;
94 	tpg->crop.width = tpg->compose.width = w;
95 	tpg->crop.height = tpg->compose.height = h;
96 	tpg->recalc_colors = true;
97 	tpg->recalc_square_border = true;
98 	tpg->brightness = 128;
99 	tpg->contrast = 128;
100 	tpg->saturation = 128;
101 	tpg->hue = 0;
102 	tpg->mv_hor_mode = TPG_MOVE_NONE;
103 	tpg->mv_vert_mode = TPG_MOVE_NONE;
104 	tpg->field = V4L2_FIELD_NONE;
105 	tpg_s_fourcc(tpg, V4L2_PIX_FMT_RGB24);
106 	tpg->colorspace = V4L2_COLORSPACE_SRGB;
107 	tpg->perc_fill = 100;
108 	tpg->hsv_enc = V4L2_HSV_ENC_180;
109 }
110 EXPORT_SYMBOL_GPL(tpg_init);
111 
112 int tpg_alloc(struct tpg_data *tpg, unsigned max_w)
113 {
114 	unsigned pat;
115 	unsigned plane;
116 
117 	tpg->max_line_width = max_w;
118 	for (pat = 0; pat < TPG_MAX_PAT_LINES; pat++) {
119 		for (plane = 0; plane < TPG_MAX_PLANES; plane++) {
120 			unsigned pixelsz = plane ? 2 : 4;
121 
122 			tpg->lines[pat][plane] =
123 				vzalloc(array3_size(max_w, 2, pixelsz));
124 			if (!tpg->lines[pat][plane])
125 				return -ENOMEM;
126 			if (plane == 0)
127 				continue;
128 			tpg->downsampled_lines[pat][plane] =
129 				vzalloc(array3_size(max_w, 2, pixelsz));
130 			if (!tpg->downsampled_lines[pat][plane])
131 				return -ENOMEM;
132 		}
133 	}
134 	for (plane = 0; plane < TPG_MAX_PLANES; plane++) {
135 		unsigned pixelsz = plane ? 2 : 4;
136 
137 		tpg->contrast_line[plane] =
138 			vzalloc(array_size(pixelsz, max_w));
139 		if (!tpg->contrast_line[plane])
140 			return -ENOMEM;
141 		tpg->black_line[plane] =
142 			vzalloc(array_size(pixelsz, max_w));
143 		if (!tpg->black_line[plane])
144 			return -ENOMEM;
145 		tpg->random_line[plane] =
146 			vzalloc(array3_size(max_w, 2, pixelsz));
147 		if (!tpg->random_line[plane])
148 			return -ENOMEM;
149 	}
150 	return 0;
151 }
152 EXPORT_SYMBOL_GPL(tpg_alloc);
153 
154 void tpg_free(struct tpg_data *tpg)
155 {
156 	unsigned pat;
157 	unsigned plane;
158 
159 	for (pat = 0; pat < TPG_MAX_PAT_LINES; pat++)
160 		for (plane = 0; plane < TPG_MAX_PLANES; plane++) {
161 			vfree(tpg->lines[pat][plane]);
162 			tpg->lines[pat][plane] = NULL;
163 			if (plane == 0)
164 				continue;
165 			vfree(tpg->downsampled_lines[pat][plane]);
166 			tpg->downsampled_lines[pat][plane] = NULL;
167 		}
168 	for (plane = 0; plane < TPG_MAX_PLANES; plane++) {
169 		vfree(tpg->contrast_line[plane]);
170 		vfree(tpg->black_line[plane]);
171 		vfree(tpg->random_line[plane]);
172 		tpg->contrast_line[plane] = NULL;
173 		tpg->black_line[plane] = NULL;
174 		tpg->random_line[plane] = NULL;
175 	}
176 }
177 EXPORT_SYMBOL_GPL(tpg_free);
178 
179 bool tpg_s_fourcc(struct tpg_data *tpg, u32 fourcc)
180 {
181 	tpg->fourcc = fourcc;
182 	tpg->planes = 1;
183 	tpg->buffers = 1;
184 	tpg->recalc_colors = true;
185 	tpg->interleaved = false;
186 	tpg->vdownsampling[0] = 1;
187 	tpg->hdownsampling[0] = 1;
188 	tpg->hmask[0] = ~0;
189 	tpg->hmask[1] = ~0;
190 	tpg->hmask[2] = ~0;
191 
192 	switch (fourcc) {
193 	case V4L2_PIX_FMT_SBGGR8:
194 	case V4L2_PIX_FMT_SGBRG8:
195 	case V4L2_PIX_FMT_SGRBG8:
196 	case V4L2_PIX_FMT_SRGGB8:
197 	case V4L2_PIX_FMT_SBGGR10:
198 	case V4L2_PIX_FMT_SGBRG10:
199 	case V4L2_PIX_FMT_SGRBG10:
200 	case V4L2_PIX_FMT_SRGGB10:
201 	case V4L2_PIX_FMT_SBGGR12:
202 	case V4L2_PIX_FMT_SGBRG12:
203 	case V4L2_PIX_FMT_SGRBG12:
204 	case V4L2_PIX_FMT_SRGGB12:
205 	case V4L2_PIX_FMT_SBGGR16:
206 	case V4L2_PIX_FMT_SGBRG16:
207 	case V4L2_PIX_FMT_SGRBG16:
208 	case V4L2_PIX_FMT_SRGGB16:
209 		tpg->interleaved = true;
210 		tpg->vdownsampling[1] = 1;
211 		tpg->hdownsampling[1] = 1;
212 		tpg->planes = 2;
213 		/* fall through */
214 	case V4L2_PIX_FMT_RGB332:
215 	case V4L2_PIX_FMT_RGB565:
216 	case V4L2_PIX_FMT_RGB565X:
217 	case V4L2_PIX_FMT_RGB444:
218 	case V4L2_PIX_FMT_XRGB444:
219 	case V4L2_PIX_FMT_ARGB444:
220 	case V4L2_PIX_FMT_RGBX444:
221 	case V4L2_PIX_FMT_RGBA444:
222 	case V4L2_PIX_FMT_XBGR444:
223 	case V4L2_PIX_FMT_ABGR444:
224 	case V4L2_PIX_FMT_BGRX444:
225 	case V4L2_PIX_FMT_BGRA444:
226 	case V4L2_PIX_FMT_RGB555:
227 	case V4L2_PIX_FMT_XRGB555:
228 	case V4L2_PIX_FMT_ARGB555:
229 	case V4L2_PIX_FMT_RGBX555:
230 	case V4L2_PIX_FMT_RGBA555:
231 	case V4L2_PIX_FMT_XBGR555:
232 	case V4L2_PIX_FMT_ABGR555:
233 	case V4L2_PIX_FMT_BGRX555:
234 	case V4L2_PIX_FMT_BGRA555:
235 	case V4L2_PIX_FMT_RGB555X:
236 	case V4L2_PIX_FMT_XRGB555X:
237 	case V4L2_PIX_FMT_ARGB555X:
238 	case V4L2_PIX_FMT_BGR666:
239 	case V4L2_PIX_FMT_RGB24:
240 	case V4L2_PIX_FMT_BGR24:
241 	case V4L2_PIX_FMT_RGB32:
242 	case V4L2_PIX_FMT_BGR32:
243 	case V4L2_PIX_FMT_XRGB32:
244 	case V4L2_PIX_FMT_XBGR32:
245 	case V4L2_PIX_FMT_ARGB32:
246 	case V4L2_PIX_FMT_ABGR32:
247 	case V4L2_PIX_FMT_RGBX32:
248 	case V4L2_PIX_FMT_BGRX32:
249 	case V4L2_PIX_FMT_RGBA32:
250 	case V4L2_PIX_FMT_BGRA32:
251 		tpg->color_enc = TGP_COLOR_ENC_RGB;
252 		break;
253 	case V4L2_PIX_FMT_GREY:
254 	case V4L2_PIX_FMT_Y10:
255 	case V4L2_PIX_FMT_Y12:
256 	case V4L2_PIX_FMT_Y16:
257 	case V4L2_PIX_FMT_Y16_BE:
258 	case V4L2_PIX_FMT_Z16:
259 		tpg->color_enc = TGP_COLOR_ENC_LUMA;
260 		break;
261 	case V4L2_PIX_FMT_YUV444:
262 	case V4L2_PIX_FMT_YUV555:
263 	case V4L2_PIX_FMT_YUV565:
264 	case V4L2_PIX_FMT_YUV32:
265 	case V4L2_PIX_FMT_AYUV32:
266 	case V4L2_PIX_FMT_XYUV32:
267 	case V4L2_PIX_FMT_VUYA32:
268 	case V4L2_PIX_FMT_VUYX32:
269 		tpg->color_enc = TGP_COLOR_ENC_YCBCR;
270 		break;
271 	case V4L2_PIX_FMT_YUV420M:
272 	case V4L2_PIX_FMT_YVU420M:
273 		tpg->buffers = 3;
274 		/* fall through */
275 	case V4L2_PIX_FMT_YUV420:
276 	case V4L2_PIX_FMT_YVU420:
277 		tpg->vdownsampling[1] = 2;
278 		tpg->vdownsampling[2] = 2;
279 		tpg->hdownsampling[1] = 2;
280 		tpg->hdownsampling[2] = 2;
281 		tpg->planes = 3;
282 		tpg->color_enc = TGP_COLOR_ENC_YCBCR;
283 		break;
284 	case V4L2_PIX_FMT_YUV422M:
285 	case V4L2_PIX_FMT_YVU422M:
286 		tpg->buffers = 3;
287 		/* fall through */
288 	case V4L2_PIX_FMT_YUV422P:
289 		tpg->vdownsampling[1] = 1;
290 		tpg->vdownsampling[2] = 1;
291 		tpg->hdownsampling[1] = 2;
292 		tpg->hdownsampling[2] = 2;
293 		tpg->planes = 3;
294 		tpg->color_enc = TGP_COLOR_ENC_YCBCR;
295 		break;
296 	case V4L2_PIX_FMT_NV16M:
297 	case V4L2_PIX_FMT_NV61M:
298 		tpg->buffers = 2;
299 		/* fall through */
300 	case V4L2_PIX_FMT_NV16:
301 	case V4L2_PIX_FMT_NV61:
302 		tpg->vdownsampling[1] = 1;
303 		tpg->hdownsampling[1] = 1;
304 		tpg->hmask[1] = ~1;
305 		tpg->planes = 2;
306 		tpg->color_enc = TGP_COLOR_ENC_YCBCR;
307 		break;
308 	case V4L2_PIX_FMT_NV12M:
309 	case V4L2_PIX_FMT_NV21M:
310 		tpg->buffers = 2;
311 		/* fall through */
312 	case V4L2_PIX_FMT_NV12:
313 	case V4L2_PIX_FMT_NV21:
314 		tpg->vdownsampling[1] = 2;
315 		tpg->hdownsampling[1] = 1;
316 		tpg->hmask[1] = ~1;
317 		tpg->planes = 2;
318 		tpg->color_enc = TGP_COLOR_ENC_YCBCR;
319 		break;
320 	case V4L2_PIX_FMT_YUV444M:
321 	case V4L2_PIX_FMT_YVU444M:
322 		tpg->buffers = 3;
323 		tpg->planes = 3;
324 		tpg->vdownsampling[1] = 1;
325 		tpg->vdownsampling[2] = 1;
326 		tpg->hdownsampling[1] = 1;
327 		tpg->hdownsampling[2] = 1;
328 		tpg->color_enc = TGP_COLOR_ENC_YCBCR;
329 		break;
330 	case V4L2_PIX_FMT_NV24:
331 	case V4L2_PIX_FMT_NV42:
332 		tpg->vdownsampling[1] = 1;
333 		tpg->hdownsampling[1] = 1;
334 		tpg->planes = 2;
335 		tpg->color_enc = TGP_COLOR_ENC_YCBCR;
336 		break;
337 	case V4L2_PIX_FMT_YUYV:
338 	case V4L2_PIX_FMT_UYVY:
339 	case V4L2_PIX_FMT_YVYU:
340 	case V4L2_PIX_FMT_VYUY:
341 		tpg->hmask[0] = ~1;
342 		tpg->color_enc = TGP_COLOR_ENC_YCBCR;
343 		break;
344 	case V4L2_PIX_FMT_HSV24:
345 	case V4L2_PIX_FMT_HSV32:
346 		tpg->color_enc = TGP_COLOR_ENC_HSV;
347 		break;
348 	default:
349 		return false;
350 	}
351 
352 	switch (fourcc) {
353 	case V4L2_PIX_FMT_GREY:
354 	case V4L2_PIX_FMT_RGB332:
355 		tpg->twopixelsize[0] = 2;
356 		break;
357 	case V4L2_PIX_FMT_RGB565:
358 	case V4L2_PIX_FMT_RGB565X:
359 	case V4L2_PIX_FMT_RGB444:
360 	case V4L2_PIX_FMT_XRGB444:
361 	case V4L2_PIX_FMT_ARGB444:
362 	case V4L2_PIX_FMT_RGBX444:
363 	case V4L2_PIX_FMT_RGBA444:
364 	case V4L2_PIX_FMT_XBGR444:
365 	case V4L2_PIX_FMT_ABGR444:
366 	case V4L2_PIX_FMT_BGRX444:
367 	case V4L2_PIX_FMT_BGRA444:
368 	case V4L2_PIX_FMT_RGB555:
369 	case V4L2_PIX_FMT_XRGB555:
370 	case V4L2_PIX_FMT_ARGB555:
371 	case V4L2_PIX_FMT_RGBX555:
372 	case V4L2_PIX_FMT_RGBA555:
373 	case V4L2_PIX_FMT_XBGR555:
374 	case V4L2_PIX_FMT_ABGR555:
375 	case V4L2_PIX_FMT_BGRX555:
376 	case V4L2_PIX_FMT_BGRA555:
377 	case V4L2_PIX_FMT_RGB555X:
378 	case V4L2_PIX_FMT_XRGB555X:
379 	case V4L2_PIX_FMT_ARGB555X:
380 	case V4L2_PIX_FMT_YUYV:
381 	case V4L2_PIX_FMT_UYVY:
382 	case V4L2_PIX_FMT_YVYU:
383 	case V4L2_PIX_FMT_VYUY:
384 	case V4L2_PIX_FMT_YUV444:
385 	case V4L2_PIX_FMT_YUV555:
386 	case V4L2_PIX_FMT_YUV565:
387 	case V4L2_PIX_FMT_Y10:
388 	case V4L2_PIX_FMT_Y12:
389 	case V4L2_PIX_FMT_Y16:
390 	case V4L2_PIX_FMT_Y16_BE:
391 	case V4L2_PIX_FMT_Z16:
392 		tpg->twopixelsize[0] = 2 * 2;
393 		break;
394 	case V4L2_PIX_FMT_RGB24:
395 	case V4L2_PIX_FMT_BGR24:
396 	case V4L2_PIX_FMT_HSV24:
397 		tpg->twopixelsize[0] = 2 * 3;
398 		break;
399 	case V4L2_PIX_FMT_BGR666:
400 	case V4L2_PIX_FMT_RGB32:
401 	case V4L2_PIX_FMT_BGR32:
402 	case V4L2_PIX_FMT_XRGB32:
403 	case V4L2_PIX_FMT_XBGR32:
404 	case V4L2_PIX_FMT_ARGB32:
405 	case V4L2_PIX_FMT_ABGR32:
406 	case V4L2_PIX_FMT_RGBX32:
407 	case V4L2_PIX_FMT_BGRX32:
408 	case V4L2_PIX_FMT_RGBA32:
409 	case V4L2_PIX_FMT_BGRA32:
410 	case V4L2_PIX_FMT_YUV32:
411 	case V4L2_PIX_FMT_AYUV32:
412 	case V4L2_PIX_FMT_XYUV32:
413 	case V4L2_PIX_FMT_VUYA32:
414 	case V4L2_PIX_FMT_VUYX32:
415 	case V4L2_PIX_FMT_HSV32:
416 		tpg->twopixelsize[0] = 2 * 4;
417 		break;
418 	case V4L2_PIX_FMT_NV12:
419 	case V4L2_PIX_FMT_NV21:
420 	case V4L2_PIX_FMT_NV12M:
421 	case V4L2_PIX_FMT_NV21M:
422 	case V4L2_PIX_FMT_NV16:
423 	case V4L2_PIX_FMT_NV61:
424 	case V4L2_PIX_FMT_NV16M:
425 	case V4L2_PIX_FMT_NV61M:
426 	case V4L2_PIX_FMT_SBGGR8:
427 	case V4L2_PIX_FMT_SGBRG8:
428 	case V4L2_PIX_FMT_SGRBG8:
429 	case V4L2_PIX_FMT_SRGGB8:
430 		tpg->twopixelsize[0] = 2;
431 		tpg->twopixelsize[1] = 2;
432 		break;
433 	case V4L2_PIX_FMT_SRGGB10:
434 	case V4L2_PIX_FMT_SGRBG10:
435 	case V4L2_PIX_FMT_SGBRG10:
436 	case V4L2_PIX_FMT_SBGGR10:
437 	case V4L2_PIX_FMT_SRGGB12:
438 	case V4L2_PIX_FMT_SGRBG12:
439 	case V4L2_PIX_FMT_SGBRG12:
440 	case V4L2_PIX_FMT_SBGGR12:
441 	case V4L2_PIX_FMT_SRGGB16:
442 	case V4L2_PIX_FMT_SGRBG16:
443 	case V4L2_PIX_FMT_SGBRG16:
444 	case V4L2_PIX_FMT_SBGGR16:
445 		tpg->twopixelsize[0] = 4;
446 		tpg->twopixelsize[1] = 4;
447 		break;
448 	case V4L2_PIX_FMT_YUV444M:
449 	case V4L2_PIX_FMT_YVU444M:
450 	case V4L2_PIX_FMT_YUV422M:
451 	case V4L2_PIX_FMT_YVU422M:
452 	case V4L2_PIX_FMT_YUV422P:
453 	case V4L2_PIX_FMT_YUV420:
454 	case V4L2_PIX_FMT_YVU420:
455 	case V4L2_PIX_FMT_YUV420M:
456 	case V4L2_PIX_FMT_YVU420M:
457 		tpg->twopixelsize[0] = 2;
458 		tpg->twopixelsize[1] = 2;
459 		tpg->twopixelsize[2] = 2;
460 		break;
461 	case V4L2_PIX_FMT_NV24:
462 	case V4L2_PIX_FMT_NV42:
463 		tpg->twopixelsize[0] = 2;
464 		tpg->twopixelsize[1] = 4;
465 		break;
466 	}
467 	return true;
468 }
469 EXPORT_SYMBOL_GPL(tpg_s_fourcc);
470 
471 void tpg_s_crop_compose(struct tpg_data *tpg, const struct v4l2_rect *crop,
472 		const struct v4l2_rect *compose)
473 {
474 	tpg->crop = *crop;
475 	tpg->compose = *compose;
476 	tpg->scaled_width = (tpg->src_width * tpg->compose.width +
477 				 tpg->crop.width - 1) / tpg->crop.width;
478 	tpg->scaled_width &= ~1;
479 	if (tpg->scaled_width > tpg->max_line_width)
480 		tpg->scaled_width = tpg->max_line_width;
481 	if (tpg->scaled_width < 2)
482 		tpg->scaled_width = 2;
483 	tpg->recalc_lines = true;
484 }
485 EXPORT_SYMBOL_GPL(tpg_s_crop_compose);
486 
487 void tpg_reset_source(struct tpg_data *tpg, unsigned width, unsigned height,
488 		       u32 field)
489 {
490 	unsigned p;
491 
492 	tpg->src_width = width;
493 	tpg->src_height = height;
494 	tpg->field = field;
495 	tpg->buf_height = height;
496 	if (V4L2_FIELD_HAS_T_OR_B(field))
497 		tpg->buf_height /= 2;
498 	tpg->scaled_width = width;
499 	tpg->crop.top = tpg->crop.left = 0;
500 	tpg->crop.width = width;
501 	tpg->crop.height = height;
502 	tpg->compose.top = tpg->compose.left = 0;
503 	tpg->compose.width = width;
504 	tpg->compose.height = tpg->buf_height;
505 	for (p = 0; p < tpg->planes; p++)
506 		tpg->bytesperline[p] = (width * tpg->twopixelsize[p]) /
507 				       (2 * tpg->hdownsampling[p]);
508 	tpg->recalc_square_border = true;
509 }
510 EXPORT_SYMBOL_GPL(tpg_reset_source);
511 
512 static enum tpg_color tpg_get_textbg_color(struct tpg_data *tpg)
513 {
514 	switch (tpg->pattern) {
515 	case TPG_PAT_BLACK:
516 		return TPG_COLOR_100_WHITE;
517 	case TPG_PAT_CSC_COLORBAR:
518 		return TPG_COLOR_CSC_BLACK;
519 	default:
520 		return TPG_COLOR_100_BLACK;
521 	}
522 }
523 
524 static enum tpg_color tpg_get_textfg_color(struct tpg_data *tpg)
525 {
526 	switch (tpg->pattern) {
527 	case TPG_PAT_75_COLORBAR:
528 	case TPG_PAT_CSC_COLORBAR:
529 		return TPG_COLOR_CSC_WHITE;
530 	case TPG_PAT_BLACK:
531 		return TPG_COLOR_100_BLACK;
532 	default:
533 		return TPG_COLOR_100_WHITE;
534 	}
535 }
536 
537 static inline int rec709_to_linear(int v)
538 {
539 	v = clamp(v, 0, 0xff0);
540 	return tpg_rec709_to_linear[v];
541 }
542 
543 static inline int linear_to_rec709(int v)
544 {
545 	v = clamp(v, 0, 0xff0);
546 	return tpg_linear_to_rec709[v];
547 }
548 
549 static void color_to_hsv(struct tpg_data *tpg, int r, int g, int b,
550 			   int *h, int *s, int *v)
551 {
552 	int max_rgb, min_rgb, diff_rgb;
553 	int aux;
554 	int third;
555 	int third_size;
556 
557 	r >>= 4;
558 	g >>= 4;
559 	b >>= 4;
560 
561 	/* Value */
562 	max_rgb = max3(r, g, b);
563 	*v = max_rgb;
564 	if (!max_rgb) {
565 		*h = 0;
566 		*s = 0;
567 		return;
568 	}
569 
570 	/* Saturation */
571 	min_rgb = min3(r, g, b);
572 	diff_rgb = max_rgb - min_rgb;
573 	aux = 255 * diff_rgb;
574 	aux += max_rgb / 2;
575 	aux /= max_rgb;
576 	*s = aux;
577 	if (!aux) {
578 		*h = 0;
579 		return;
580 	}
581 
582 	third_size = (tpg->real_hsv_enc == V4L2_HSV_ENC_180) ? 60 : 85;
583 
584 	/* Hue */
585 	if (max_rgb == r) {
586 		aux =  g - b;
587 		third = 0;
588 	} else if (max_rgb == g) {
589 		aux =  b - r;
590 		third = third_size;
591 	} else {
592 		aux =  r - g;
593 		third = third_size * 2;
594 	}
595 
596 	aux *= third_size / 2;
597 	aux += diff_rgb / 2;
598 	aux /= diff_rgb;
599 	aux += third;
600 
601 	/* Clamp Hue */
602 	if (tpg->real_hsv_enc == V4L2_HSV_ENC_180) {
603 		if (aux < 0)
604 			aux += 180;
605 		else if (aux > 180)
606 			aux -= 180;
607 	} else {
608 		aux = aux & 0xff;
609 	}
610 
611 	*h = aux;
612 }
613 
614 static void rgb2ycbcr(const int m[3][3], int r, int g, int b,
615 			int y_offset, int *y, int *cb, int *cr)
616 {
617 	*y  = ((m[0][0] * r + m[0][1] * g + m[0][2] * b) >> 16) + (y_offset << 4);
618 	*cb = ((m[1][0] * r + m[1][1] * g + m[1][2] * b) >> 16) + (128 << 4);
619 	*cr = ((m[2][0] * r + m[2][1] * g + m[2][2] * b) >> 16) + (128 << 4);
620 }
621 
622 static void color_to_ycbcr(struct tpg_data *tpg, int r, int g, int b,
623 			   int *y, int *cb, int *cr)
624 {
625 #define COEFF(v, r) ((int)(0.5 + (v) * (r) * 256.0))
626 
627 	static const int bt601[3][3] = {
628 		{ COEFF(0.299, 219),   COEFF(0.587, 219),   COEFF(0.114, 219)   },
629 		{ COEFF(-0.1687, 224), COEFF(-0.3313, 224), COEFF(0.5, 224)     },
630 		{ COEFF(0.5, 224),     COEFF(-0.4187, 224), COEFF(-0.0813, 224) },
631 	};
632 	static const int bt601_full[3][3] = {
633 		{ COEFF(0.299, 255),   COEFF(0.587, 255),   COEFF(0.114, 255)   },
634 		{ COEFF(-0.1687, 255), COEFF(-0.3313, 255), COEFF(0.5, 255)     },
635 		{ COEFF(0.5, 255),     COEFF(-0.4187, 255), COEFF(-0.0813, 255) },
636 	};
637 	static const int rec709[3][3] = {
638 		{ COEFF(0.2126, 219),  COEFF(0.7152, 219),  COEFF(0.0722, 219)  },
639 		{ COEFF(-0.1146, 224), COEFF(-0.3854, 224), COEFF(0.5, 224)     },
640 		{ COEFF(0.5, 224),     COEFF(-0.4542, 224), COEFF(-0.0458, 224) },
641 	};
642 	static const int rec709_full[3][3] = {
643 		{ COEFF(0.2126, 255),  COEFF(0.7152, 255),  COEFF(0.0722, 255)  },
644 		{ COEFF(-0.1146, 255), COEFF(-0.3854, 255), COEFF(0.5, 255)     },
645 		{ COEFF(0.5, 255),     COEFF(-0.4542, 255), COEFF(-0.0458, 255) },
646 	};
647 	static const int smpte240m[3][3] = {
648 		{ COEFF(0.212, 219),  COEFF(0.701, 219),  COEFF(0.087, 219)  },
649 		{ COEFF(-0.116, 224), COEFF(-0.384, 224), COEFF(0.5, 224)    },
650 		{ COEFF(0.5, 224),    COEFF(-0.445, 224), COEFF(-0.055, 224) },
651 	};
652 	static const int smpte240m_full[3][3] = {
653 		{ COEFF(0.212, 255),  COEFF(0.701, 255),  COEFF(0.087, 255)  },
654 		{ COEFF(-0.116, 255), COEFF(-0.384, 255), COEFF(0.5, 255)    },
655 		{ COEFF(0.5, 255),    COEFF(-0.445, 255), COEFF(-0.055, 255) },
656 	};
657 	static const int bt2020[3][3] = {
658 		{ COEFF(0.2627, 219),  COEFF(0.6780, 219),  COEFF(0.0593, 219)  },
659 		{ COEFF(-0.1396, 224), COEFF(-0.3604, 224), COEFF(0.5, 224)     },
660 		{ COEFF(0.5, 224),     COEFF(-0.4598, 224), COEFF(-0.0402, 224) },
661 	};
662 	static const int bt2020_full[3][3] = {
663 		{ COEFF(0.2627, 255),  COEFF(0.6780, 255),  COEFF(0.0593, 255)  },
664 		{ COEFF(-0.1396, 255), COEFF(-0.3604, 255), COEFF(0.5, 255)     },
665 		{ COEFF(0.5, 255),     COEFF(-0.4598, 255), COEFF(-0.0402, 255) },
666 	};
667 	static const int bt2020c[4] = {
668 		COEFF(1.0 / 1.9404, 224), COEFF(1.0 / 1.5816, 224),
669 		COEFF(1.0 / 1.7184, 224), COEFF(1.0 / 0.9936, 224),
670 	};
671 	static const int bt2020c_full[4] = {
672 		COEFF(1.0 / 1.9404, 255), COEFF(1.0 / 1.5816, 255),
673 		COEFF(1.0 / 1.7184, 255), COEFF(1.0 / 0.9936, 255),
674 	};
675 
676 	bool full = tpg->real_quantization == V4L2_QUANTIZATION_FULL_RANGE;
677 	unsigned y_offset = full ? 0 : 16;
678 	int lin_y, yc;
679 
680 	switch (tpg->real_ycbcr_enc) {
681 	case V4L2_YCBCR_ENC_601:
682 		rgb2ycbcr(full ? bt601_full : bt601, r, g, b, y_offset, y, cb, cr);
683 		break;
684 	case V4L2_YCBCR_ENC_XV601:
685 		/* Ignore quantization range, there is only one possible
686 		 * Y'CbCr encoding. */
687 		rgb2ycbcr(bt601, r, g, b, 16, y, cb, cr);
688 		break;
689 	case V4L2_YCBCR_ENC_XV709:
690 		/* Ignore quantization range, there is only one possible
691 		 * Y'CbCr encoding. */
692 		rgb2ycbcr(rec709, r, g, b, 16, y, cb, cr);
693 		break;
694 	case V4L2_YCBCR_ENC_BT2020:
695 		rgb2ycbcr(full ? bt2020_full : bt2020, r, g, b, y_offset, y, cb, cr);
696 		break;
697 	case V4L2_YCBCR_ENC_BT2020_CONST_LUM:
698 		lin_y = (COEFF(0.2627, 255) * rec709_to_linear(r) +
699 			 COEFF(0.6780, 255) * rec709_to_linear(g) +
700 			 COEFF(0.0593, 255) * rec709_to_linear(b)) >> 16;
701 		yc = linear_to_rec709(lin_y);
702 		*y = full ? yc : (yc * 219) / 255 + (16 << 4);
703 		if (b <= yc)
704 			*cb = (((b - yc) * (full ? bt2020c_full[0] : bt2020c[0])) >> 16) + (128 << 4);
705 		else
706 			*cb = (((b - yc) * (full ? bt2020c_full[1] : bt2020c[1])) >> 16) + (128 << 4);
707 		if (r <= yc)
708 			*cr = (((r - yc) * (full ? bt2020c_full[2] : bt2020c[2])) >> 16) + (128 << 4);
709 		else
710 			*cr = (((r - yc) * (full ? bt2020c_full[3] : bt2020c[3])) >> 16) + (128 << 4);
711 		break;
712 	case V4L2_YCBCR_ENC_SMPTE240M:
713 		rgb2ycbcr(full ? smpte240m_full : smpte240m, r, g, b, y_offset, y, cb, cr);
714 		break;
715 	case V4L2_YCBCR_ENC_709:
716 	default:
717 		rgb2ycbcr(full ? rec709_full : rec709, r, g, b, y_offset, y, cb, cr);
718 		break;
719 	}
720 }
721 
722 static void ycbcr2rgb(const int m[3][3], int y, int cb, int cr,
723 			int y_offset, int *r, int *g, int *b)
724 {
725 	y -= y_offset << 4;
726 	cb -= 128 << 4;
727 	cr -= 128 << 4;
728 	*r = m[0][0] * y + m[0][1] * cb + m[0][2] * cr;
729 	*g = m[1][0] * y + m[1][1] * cb + m[1][2] * cr;
730 	*b = m[2][0] * y + m[2][1] * cb + m[2][2] * cr;
731 	*r = clamp(*r >> 12, 0, 0xff0);
732 	*g = clamp(*g >> 12, 0, 0xff0);
733 	*b = clamp(*b >> 12, 0, 0xff0);
734 }
735 
736 static void ycbcr_to_color(struct tpg_data *tpg, int y, int cb, int cr,
737 			   int *r, int *g, int *b)
738 {
739 #undef COEFF
740 #define COEFF(v, r) ((int)(0.5 + (v) * ((255.0 * 255.0 * 16.0) / (r))))
741 	static const int bt601[3][3] = {
742 		{ COEFF(1, 219), COEFF(0, 224),       COEFF(1.4020, 224)  },
743 		{ COEFF(1, 219), COEFF(-0.3441, 224), COEFF(-0.7141, 224) },
744 		{ COEFF(1, 219), COEFF(1.7720, 224),  COEFF(0, 224)       },
745 	};
746 	static const int bt601_full[3][3] = {
747 		{ COEFF(1, 255), COEFF(0, 255),       COEFF(1.4020, 255)  },
748 		{ COEFF(1, 255), COEFF(-0.3441, 255), COEFF(-0.7141, 255) },
749 		{ COEFF(1, 255), COEFF(1.7720, 255),  COEFF(0, 255)       },
750 	};
751 	static const int rec709[3][3] = {
752 		{ COEFF(1, 219), COEFF(0, 224),       COEFF(1.5748, 224)  },
753 		{ COEFF(1, 219), COEFF(-0.1873, 224), COEFF(-0.4681, 224) },
754 		{ COEFF(1, 219), COEFF(1.8556, 224),  COEFF(0, 224)       },
755 	};
756 	static const int rec709_full[3][3] = {
757 		{ COEFF(1, 255), COEFF(0, 255),       COEFF(1.5748, 255)  },
758 		{ COEFF(1, 255), COEFF(-0.1873, 255), COEFF(-0.4681, 255) },
759 		{ COEFF(1, 255), COEFF(1.8556, 255),  COEFF(0, 255)       },
760 	};
761 	static const int smpte240m[3][3] = {
762 		{ COEFF(1, 219), COEFF(0, 224),       COEFF(1.5756, 224)  },
763 		{ COEFF(1, 219), COEFF(-0.2253, 224), COEFF(-0.4767, 224) },
764 		{ COEFF(1, 219), COEFF(1.8270, 224),  COEFF(0, 224)       },
765 	};
766 	static const int smpte240m_full[3][3] = {
767 		{ COEFF(1, 255), COEFF(0, 255),       COEFF(1.5756, 255)  },
768 		{ COEFF(1, 255), COEFF(-0.2253, 255), COEFF(-0.4767, 255) },
769 		{ COEFF(1, 255), COEFF(1.8270, 255),  COEFF(0, 255)       },
770 	};
771 	static const int bt2020[3][3] = {
772 		{ COEFF(1, 219), COEFF(0, 224),       COEFF(1.4746, 224)  },
773 		{ COEFF(1, 219), COEFF(-0.1646, 224), COEFF(-0.5714, 224) },
774 		{ COEFF(1, 219), COEFF(1.8814, 224),  COEFF(0, 224)       },
775 	};
776 	static const int bt2020_full[3][3] = {
777 		{ COEFF(1, 255), COEFF(0, 255),       COEFF(1.4746, 255)  },
778 		{ COEFF(1, 255), COEFF(-0.1646, 255), COEFF(-0.5714, 255) },
779 		{ COEFF(1, 255), COEFF(1.8814, 255),  COEFF(0, 255)       },
780 	};
781 	static const int bt2020c[4] = {
782 		COEFF(1.9404, 224), COEFF(1.5816, 224),
783 		COEFF(1.7184, 224), COEFF(0.9936, 224),
784 	};
785 	static const int bt2020c_full[4] = {
786 		COEFF(1.9404, 255), COEFF(1.5816, 255),
787 		COEFF(1.7184, 255), COEFF(0.9936, 255),
788 	};
789 
790 	bool full = tpg->real_quantization == V4L2_QUANTIZATION_FULL_RANGE;
791 	unsigned y_offset = full ? 0 : 16;
792 	int y_fac = full ? COEFF(1.0, 255) : COEFF(1.0, 219);
793 	int lin_r, lin_g, lin_b, lin_y;
794 
795 	switch (tpg->real_ycbcr_enc) {
796 	case V4L2_YCBCR_ENC_601:
797 		ycbcr2rgb(full ? bt601_full : bt601, y, cb, cr, y_offset, r, g, b);
798 		break;
799 	case V4L2_YCBCR_ENC_XV601:
800 		/* Ignore quantization range, there is only one possible
801 		 * Y'CbCr encoding. */
802 		ycbcr2rgb(bt601, y, cb, cr, 16, r, g, b);
803 		break;
804 	case V4L2_YCBCR_ENC_XV709:
805 		/* Ignore quantization range, there is only one possible
806 		 * Y'CbCr encoding. */
807 		ycbcr2rgb(rec709, y, cb, cr, 16, r, g, b);
808 		break;
809 	case V4L2_YCBCR_ENC_BT2020:
810 		ycbcr2rgb(full ? bt2020_full : bt2020, y, cb, cr, y_offset, r, g, b);
811 		break;
812 	case V4L2_YCBCR_ENC_BT2020_CONST_LUM:
813 		y -= full ? 0 : 16 << 4;
814 		cb -= 128 << 4;
815 		cr -= 128 << 4;
816 
817 		if (cb <= 0)
818 			*b = y_fac * y + (full ? bt2020c_full[0] : bt2020c[0]) * cb;
819 		else
820 			*b = y_fac * y + (full ? bt2020c_full[1] : bt2020c[1]) * cb;
821 		*b = *b >> 12;
822 		if (cr <= 0)
823 			*r = y_fac * y + (full ? bt2020c_full[2] : bt2020c[2]) * cr;
824 		else
825 			*r = y_fac * y + (full ? bt2020c_full[3] : bt2020c[3]) * cr;
826 		*r = *r >> 12;
827 		lin_r = rec709_to_linear(*r);
828 		lin_b = rec709_to_linear(*b);
829 		lin_y = rec709_to_linear((y * 255) / (full ? 255 : 219));
830 
831 		lin_g = COEFF(1.0 / 0.6780, 255) * lin_y -
832 			COEFF(0.2627 / 0.6780, 255) * lin_r -
833 			COEFF(0.0593 / 0.6780, 255) * lin_b;
834 		*g = linear_to_rec709(lin_g >> 12);
835 		break;
836 	case V4L2_YCBCR_ENC_SMPTE240M:
837 		ycbcr2rgb(full ? smpte240m_full : smpte240m, y, cb, cr, y_offset, r, g, b);
838 		break;
839 	case V4L2_YCBCR_ENC_709:
840 	default:
841 		ycbcr2rgb(full ? rec709_full : rec709, y, cb, cr, y_offset, r, g, b);
842 		break;
843 	}
844 }
845 
846 /* precalculate color bar values to speed up rendering */
847 static void precalculate_color(struct tpg_data *tpg, int k)
848 {
849 	int col = k;
850 	int r = tpg_colors[col].r;
851 	int g = tpg_colors[col].g;
852 	int b = tpg_colors[col].b;
853 	int y, cb, cr;
854 	bool ycbcr_valid = false;
855 
856 	if (k == TPG_COLOR_TEXTBG) {
857 		col = tpg_get_textbg_color(tpg);
858 
859 		r = tpg_colors[col].r;
860 		g = tpg_colors[col].g;
861 		b = tpg_colors[col].b;
862 	} else if (k == TPG_COLOR_TEXTFG) {
863 		col = tpg_get_textfg_color(tpg);
864 
865 		r = tpg_colors[col].r;
866 		g = tpg_colors[col].g;
867 		b = tpg_colors[col].b;
868 	} else if (tpg->pattern == TPG_PAT_NOISE) {
869 		r = g = b = prandom_u32_max(256);
870 	} else if (k == TPG_COLOR_RANDOM) {
871 		r = g = b = tpg->qual_offset + prandom_u32_max(196);
872 	} else if (k >= TPG_COLOR_RAMP) {
873 		r = g = b = k - TPG_COLOR_RAMP;
874 	}
875 
876 	if (tpg->pattern == TPG_PAT_CSC_COLORBAR && col <= TPG_COLOR_CSC_BLACK) {
877 		r = tpg_csc_colors[tpg->colorspace][tpg->real_xfer_func][col].r;
878 		g = tpg_csc_colors[tpg->colorspace][tpg->real_xfer_func][col].g;
879 		b = tpg_csc_colors[tpg->colorspace][tpg->real_xfer_func][col].b;
880 	} else {
881 		r <<= 4;
882 		g <<= 4;
883 		b <<= 4;
884 	}
885 
886 	if (tpg->qual == TPG_QUAL_GRAY ||
887 	    tpg->color_enc ==  TGP_COLOR_ENC_LUMA) {
888 		/* Rec. 709 Luma function */
889 		/* (0.2126, 0.7152, 0.0722) * (255 * 256) */
890 		r = g = b = (13879 * r + 46688 * g + 4713 * b) >> 16;
891 	}
892 
893 	/*
894 	 * The assumption is that the RGB output is always full range,
895 	 * so only if the rgb_range overrides the 'real' rgb range do
896 	 * we need to convert the RGB values.
897 	 *
898 	 * Remember that r, g and b are still in the 0 - 0xff0 range.
899 	 */
900 	if (tpg->real_rgb_range == V4L2_DV_RGB_RANGE_LIMITED &&
901 	    tpg->rgb_range == V4L2_DV_RGB_RANGE_FULL &&
902 	    tpg->color_enc == TGP_COLOR_ENC_RGB) {
903 		/*
904 		 * Convert from full range (which is what r, g and b are)
905 		 * to limited range (which is the 'real' RGB range), which
906 		 * is then interpreted as full range.
907 		 */
908 		r = (r * 219) / 255 + (16 << 4);
909 		g = (g * 219) / 255 + (16 << 4);
910 		b = (b * 219) / 255 + (16 << 4);
911 	} else if (tpg->real_rgb_range != V4L2_DV_RGB_RANGE_LIMITED &&
912 		   tpg->rgb_range == V4L2_DV_RGB_RANGE_LIMITED &&
913 		   tpg->color_enc == TGP_COLOR_ENC_RGB) {
914 
915 		/*
916 		 * Clamp r, g and b to the limited range and convert to full
917 		 * range since that's what we deliver.
918 		 */
919 		r = clamp(r, 16 << 4, 235 << 4);
920 		g = clamp(g, 16 << 4, 235 << 4);
921 		b = clamp(b, 16 << 4, 235 << 4);
922 		r = (r - (16 << 4)) * 255 / 219;
923 		g = (g - (16 << 4)) * 255 / 219;
924 		b = (b - (16 << 4)) * 255 / 219;
925 	}
926 
927 	if ((tpg->brightness != 128 || tpg->contrast != 128 ||
928 	     tpg->saturation != 128 || tpg->hue) &&
929 	    tpg->color_enc != TGP_COLOR_ENC_LUMA) {
930 		/* Implement these operations */
931 		int tmp_cb, tmp_cr;
932 
933 		/* First convert to YCbCr */
934 
935 		color_to_ycbcr(tpg, r, g, b, &y, &cb, &cr);
936 
937 		y = (16 << 4) + ((y - (16 << 4)) * tpg->contrast) / 128;
938 		y += (tpg->brightness << 4) - (128 << 4);
939 
940 		cb -= 128 << 4;
941 		cr -= 128 << 4;
942 		tmp_cb = (cb * cos(128 + tpg->hue)) / 127 + (cr * sin[128 + tpg->hue]) / 127;
943 		tmp_cr = (cr * cos(128 + tpg->hue)) / 127 - (cb * sin[128 + tpg->hue]) / 127;
944 
945 		cb = (128 << 4) + (tmp_cb * tpg->contrast * tpg->saturation) / (128 * 128);
946 		cr = (128 << 4) + (tmp_cr * tpg->contrast * tpg->saturation) / (128 * 128);
947 		if (tpg->color_enc == TGP_COLOR_ENC_YCBCR)
948 			ycbcr_valid = true;
949 		else
950 			ycbcr_to_color(tpg, y, cb, cr, &r, &g, &b);
951 	} else if ((tpg->brightness != 128 || tpg->contrast != 128) &&
952 		   tpg->color_enc == TGP_COLOR_ENC_LUMA) {
953 		r = (16 << 4) + ((r - (16 << 4)) * tpg->contrast) / 128;
954 		r += (tpg->brightness << 4) - (128 << 4);
955 	}
956 
957 	switch (tpg->color_enc) {
958 	case TGP_COLOR_ENC_HSV:
959 	{
960 		int h, s, v;
961 
962 		color_to_hsv(tpg, r, g, b, &h, &s, &v);
963 		tpg->colors[k][0] = h;
964 		tpg->colors[k][1] = s;
965 		tpg->colors[k][2] = v;
966 		break;
967 	}
968 	case TGP_COLOR_ENC_YCBCR:
969 	{
970 		/* Convert to YCbCr */
971 		if (!ycbcr_valid)
972 			color_to_ycbcr(tpg, r, g, b, &y, &cb, &cr);
973 
974 		y >>= 4;
975 		cb >>= 4;
976 		cr >>= 4;
977 		/*
978 		 * XV601/709 use the header/footer margins to encode R', G'
979 		 * and B' values outside the range [0-1]. So do not clamp
980 		 * XV601/709 values.
981 		 */
982 		if (tpg->real_quantization == V4L2_QUANTIZATION_LIM_RANGE &&
983 		    tpg->real_ycbcr_enc != V4L2_YCBCR_ENC_XV601 &&
984 		    tpg->real_ycbcr_enc != V4L2_YCBCR_ENC_XV709) {
985 			y = clamp(y, 16, 235);
986 			cb = clamp(cb, 16, 240);
987 			cr = clamp(cr, 16, 240);
988 		} else {
989 			y = clamp(y, 1, 254);
990 			cb = clamp(cb, 1, 254);
991 			cr = clamp(cr, 1, 254);
992 		}
993 		switch (tpg->fourcc) {
994 		case V4L2_PIX_FMT_YUV444:
995 			y >>= 4;
996 			cb >>= 4;
997 			cr >>= 4;
998 			break;
999 		case V4L2_PIX_FMT_YUV555:
1000 			y >>= 3;
1001 			cb >>= 3;
1002 			cr >>= 3;
1003 			break;
1004 		case V4L2_PIX_FMT_YUV565:
1005 			y >>= 3;
1006 			cb >>= 2;
1007 			cr >>= 3;
1008 			break;
1009 		}
1010 		tpg->colors[k][0] = y;
1011 		tpg->colors[k][1] = cb;
1012 		tpg->colors[k][2] = cr;
1013 		break;
1014 	}
1015 	case TGP_COLOR_ENC_LUMA:
1016 	{
1017 		tpg->colors[k][0] = r >> 4;
1018 		break;
1019 	}
1020 	case TGP_COLOR_ENC_RGB:
1021 	{
1022 		if (tpg->real_quantization == V4L2_QUANTIZATION_LIM_RANGE) {
1023 			r = (r * 219) / 255 + (16 << 4);
1024 			g = (g * 219) / 255 + (16 << 4);
1025 			b = (b * 219) / 255 + (16 << 4);
1026 		}
1027 		switch (tpg->fourcc) {
1028 		case V4L2_PIX_FMT_RGB332:
1029 			r >>= 9;
1030 			g >>= 9;
1031 			b >>= 10;
1032 			break;
1033 		case V4L2_PIX_FMT_RGB565:
1034 		case V4L2_PIX_FMT_RGB565X:
1035 			r >>= 7;
1036 			g >>= 6;
1037 			b >>= 7;
1038 			break;
1039 		case V4L2_PIX_FMT_RGB444:
1040 		case V4L2_PIX_FMT_XRGB444:
1041 		case V4L2_PIX_FMT_ARGB444:
1042 		case V4L2_PIX_FMT_RGBX444:
1043 		case V4L2_PIX_FMT_RGBA444:
1044 		case V4L2_PIX_FMT_XBGR444:
1045 		case V4L2_PIX_FMT_ABGR444:
1046 		case V4L2_PIX_FMT_BGRX444:
1047 		case V4L2_PIX_FMT_BGRA444:
1048 			r >>= 8;
1049 			g >>= 8;
1050 			b >>= 8;
1051 			break;
1052 		case V4L2_PIX_FMT_RGB555:
1053 		case V4L2_PIX_FMT_XRGB555:
1054 		case V4L2_PIX_FMT_ARGB555:
1055 		case V4L2_PIX_FMT_RGBX555:
1056 		case V4L2_PIX_FMT_RGBA555:
1057 		case V4L2_PIX_FMT_XBGR555:
1058 		case V4L2_PIX_FMT_ABGR555:
1059 		case V4L2_PIX_FMT_BGRX555:
1060 		case V4L2_PIX_FMT_BGRA555:
1061 		case V4L2_PIX_FMT_RGB555X:
1062 		case V4L2_PIX_FMT_XRGB555X:
1063 		case V4L2_PIX_FMT_ARGB555X:
1064 			r >>= 7;
1065 			g >>= 7;
1066 			b >>= 7;
1067 			break;
1068 		case V4L2_PIX_FMT_BGR666:
1069 			r >>= 6;
1070 			g >>= 6;
1071 			b >>= 6;
1072 			break;
1073 		default:
1074 			r >>= 4;
1075 			g >>= 4;
1076 			b >>= 4;
1077 			break;
1078 		}
1079 
1080 		tpg->colors[k][0] = r;
1081 		tpg->colors[k][1] = g;
1082 		tpg->colors[k][2] = b;
1083 		break;
1084 	}
1085 	}
1086 }
1087 
1088 static void tpg_precalculate_colors(struct tpg_data *tpg)
1089 {
1090 	int k;
1091 
1092 	for (k = 0; k < TPG_COLOR_MAX; k++)
1093 		precalculate_color(tpg, k);
1094 }
1095 
1096 /* 'odd' is true for pixels 1, 3, 5, etc. and false for pixels 0, 2, 4, etc. */
1097 static void gen_twopix(struct tpg_data *tpg,
1098 		u8 buf[TPG_MAX_PLANES][8], int color, bool odd)
1099 {
1100 	unsigned offset = odd * tpg->twopixelsize[0] / 2;
1101 	u8 alpha = tpg->alpha_component;
1102 	u8 r_y_h, g_u_s, b_v;
1103 
1104 	if (tpg->alpha_red_only && color != TPG_COLOR_CSC_RED &&
1105 				   color != TPG_COLOR_100_RED &&
1106 				   color != TPG_COLOR_75_RED)
1107 		alpha = 0;
1108 	if (color == TPG_COLOR_RANDOM)
1109 		precalculate_color(tpg, color);
1110 	r_y_h = tpg->colors[color][0]; /* R or precalculated Y, H */
1111 	g_u_s = tpg->colors[color][1]; /* G or precalculated U, V */
1112 	b_v = tpg->colors[color][2]; /* B or precalculated V */
1113 
1114 	switch (tpg->fourcc) {
1115 	case V4L2_PIX_FMT_GREY:
1116 		buf[0][offset] = r_y_h;
1117 		break;
1118 	case V4L2_PIX_FMT_Y10:
1119 		buf[0][offset] = (r_y_h << 2) & 0xff;
1120 		buf[0][offset+1] = r_y_h >> 6;
1121 		break;
1122 	case V4L2_PIX_FMT_Y12:
1123 		buf[0][offset] = (r_y_h << 4) & 0xff;
1124 		buf[0][offset+1] = r_y_h >> 4;
1125 		break;
1126 	case V4L2_PIX_FMT_Y16:
1127 	case V4L2_PIX_FMT_Z16:
1128 		/*
1129 		 * Ideally both bytes should be set to r_y_h, but then you won't
1130 		 * be able to detect endian problems. So keep it 0 except for
1131 		 * the corner case where r_y_h is 0xff so white really will be
1132 		 * white (0xffff).
1133 		 */
1134 		buf[0][offset] = r_y_h == 0xff ? r_y_h : 0;
1135 		buf[0][offset+1] = r_y_h;
1136 		break;
1137 	case V4L2_PIX_FMT_Y16_BE:
1138 		/* See comment for V4L2_PIX_FMT_Y16 above */
1139 		buf[0][offset] = r_y_h;
1140 		buf[0][offset+1] = r_y_h == 0xff ? r_y_h : 0;
1141 		break;
1142 	case V4L2_PIX_FMT_YUV422M:
1143 	case V4L2_PIX_FMT_YUV422P:
1144 	case V4L2_PIX_FMT_YUV420:
1145 	case V4L2_PIX_FMT_YUV420M:
1146 		buf[0][offset] = r_y_h;
1147 		if (odd) {
1148 			buf[1][0] = (buf[1][0] + g_u_s) / 2;
1149 			buf[2][0] = (buf[2][0] + b_v) / 2;
1150 			buf[1][1] = buf[1][0];
1151 			buf[2][1] = buf[2][0];
1152 			break;
1153 		}
1154 		buf[1][0] = g_u_s;
1155 		buf[2][0] = b_v;
1156 		break;
1157 	case V4L2_PIX_FMT_YVU422M:
1158 	case V4L2_PIX_FMT_YVU420:
1159 	case V4L2_PIX_FMT_YVU420M:
1160 		buf[0][offset] = r_y_h;
1161 		if (odd) {
1162 			buf[1][0] = (buf[1][0] + b_v) / 2;
1163 			buf[2][0] = (buf[2][0] + g_u_s) / 2;
1164 			buf[1][1] = buf[1][0];
1165 			buf[2][1] = buf[2][0];
1166 			break;
1167 		}
1168 		buf[1][0] = b_v;
1169 		buf[2][0] = g_u_s;
1170 		break;
1171 
1172 	case V4L2_PIX_FMT_NV12:
1173 	case V4L2_PIX_FMT_NV12M:
1174 	case V4L2_PIX_FMT_NV16:
1175 	case V4L2_PIX_FMT_NV16M:
1176 		buf[0][offset] = r_y_h;
1177 		if (odd) {
1178 			buf[1][0] = (buf[1][0] + g_u_s) / 2;
1179 			buf[1][1] = (buf[1][1] + b_v) / 2;
1180 			break;
1181 		}
1182 		buf[1][0] = g_u_s;
1183 		buf[1][1] = b_v;
1184 		break;
1185 	case V4L2_PIX_FMT_NV21:
1186 	case V4L2_PIX_FMT_NV21M:
1187 	case V4L2_PIX_FMT_NV61:
1188 	case V4L2_PIX_FMT_NV61M:
1189 		buf[0][offset] = r_y_h;
1190 		if (odd) {
1191 			buf[1][0] = (buf[1][0] + b_v) / 2;
1192 			buf[1][1] = (buf[1][1] + g_u_s) / 2;
1193 			break;
1194 		}
1195 		buf[1][0] = b_v;
1196 		buf[1][1] = g_u_s;
1197 		break;
1198 
1199 	case V4L2_PIX_FMT_YUV444M:
1200 		buf[0][offset] = r_y_h;
1201 		buf[1][offset] = g_u_s;
1202 		buf[2][offset] = b_v;
1203 		break;
1204 
1205 	case V4L2_PIX_FMT_YVU444M:
1206 		buf[0][offset] = r_y_h;
1207 		buf[1][offset] = b_v;
1208 		buf[2][offset] = g_u_s;
1209 		break;
1210 
1211 	case V4L2_PIX_FMT_NV24:
1212 		buf[0][offset] = r_y_h;
1213 		buf[1][2 * offset] = g_u_s;
1214 		buf[1][(2 * offset + 1) % 8] = b_v;
1215 		break;
1216 
1217 	case V4L2_PIX_FMT_NV42:
1218 		buf[0][offset] = r_y_h;
1219 		buf[1][2 * offset] = b_v;
1220 		buf[1][(2 * offset + 1) % 8] = g_u_s;
1221 		break;
1222 
1223 	case V4L2_PIX_FMT_YUYV:
1224 		buf[0][offset] = r_y_h;
1225 		if (odd) {
1226 			buf[0][1] = (buf[0][1] + g_u_s) / 2;
1227 			buf[0][3] = (buf[0][3] + b_v) / 2;
1228 			break;
1229 		}
1230 		buf[0][1] = g_u_s;
1231 		buf[0][3] = b_v;
1232 		break;
1233 	case V4L2_PIX_FMT_UYVY:
1234 		buf[0][offset + 1] = r_y_h;
1235 		if (odd) {
1236 			buf[0][0] = (buf[0][0] + g_u_s) / 2;
1237 			buf[0][2] = (buf[0][2] + b_v) / 2;
1238 			break;
1239 		}
1240 		buf[0][0] = g_u_s;
1241 		buf[0][2] = b_v;
1242 		break;
1243 	case V4L2_PIX_FMT_YVYU:
1244 		buf[0][offset] = r_y_h;
1245 		if (odd) {
1246 			buf[0][1] = (buf[0][1] + b_v) / 2;
1247 			buf[0][3] = (buf[0][3] + g_u_s) / 2;
1248 			break;
1249 		}
1250 		buf[0][1] = b_v;
1251 		buf[0][3] = g_u_s;
1252 		break;
1253 	case V4L2_PIX_FMT_VYUY:
1254 		buf[0][offset + 1] = r_y_h;
1255 		if (odd) {
1256 			buf[0][0] = (buf[0][0] + b_v) / 2;
1257 			buf[0][2] = (buf[0][2] + g_u_s) / 2;
1258 			break;
1259 		}
1260 		buf[0][0] = b_v;
1261 		buf[0][2] = g_u_s;
1262 		break;
1263 	case V4L2_PIX_FMT_RGB332:
1264 		buf[0][offset] = (r_y_h << 5) | (g_u_s << 2) | b_v;
1265 		break;
1266 	case V4L2_PIX_FMT_YUV565:
1267 	case V4L2_PIX_FMT_RGB565:
1268 		buf[0][offset] = (g_u_s << 5) | b_v;
1269 		buf[0][offset + 1] = (r_y_h << 3) | (g_u_s >> 3);
1270 		break;
1271 	case V4L2_PIX_FMT_RGB565X:
1272 		buf[0][offset] = (r_y_h << 3) | (g_u_s >> 3);
1273 		buf[0][offset + 1] = (g_u_s << 5) | b_v;
1274 		break;
1275 	case V4L2_PIX_FMT_RGB444:
1276 	case V4L2_PIX_FMT_XRGB444:
1277 		alpha = 0;
1278 		/* fall through */
1279 	case V4L2_PIX_FMT_YUV444:
1280 	case V4L2_PIX_FMT_ARGB444:
1281 		buf[0][offset] = (g_u_s << 4) | b_v;
1282 		buf[0][offset + 1] = (alpha & 0xf0) | r_y_h;
1283 		break;
1284 	case V4L2_PIX_FMT_RGBX444:
1285 		alpha = 0;
1286 		/* fall through */
1287 	case V4L2_PIX_FMT_RGBA444:
1288 		buf[0][offset] = (b_v << 4) | (alpha >> 4);
1289 		buf[0][offset + 1] = (r_y_h << 4) | g_u_s;
1290 		break;
1291 	case V4L2_PIX_FMT_XBGR444:
1292 		alpha = 0;
1293 		/* fall through */
1294 	case V4L2_PIX_FMT_ABGR444:
1295 		buf[0][offset] = (g_u_s << 4) | r_y_h;
1296 		buf[0][offset + 1] = (alpha & 0xf0) | b_v;
1297 		break;
1298 	case V4L2_PIX_FMT_BGRX444:
1299 		alpha = 0;
1300 		/* fall through */
1301 	case V4L2_PIX_FMT_BGRA444:
1302 		buf[0][offset] = (r_y_h << 4) | (alpha >> 4);
1303 		buf[0][offset + 1] = (b_v << 4) | g_u_s;
1304 		break;
1305 	case V4L2_PIX_FMT_RGB555:
1306 	case V4L2_PIX_FMT_XRGB555:
1307 		alpha = 0;
1308 		/* fall through */
1309 	case V4L2_PIX_FMT_YUV555:
1310 	case V4L2_PIX_FMT_ARGB555:
1311 		buf[0][offset] = (g_u_s << 5) | b_v;
1312 		buf[0][offset + 1] = (alpha & 0x80) | (r_y_h << 2)
1313 						    | (g_u_s >> 3);
1314 		break;
1315 	case V4L2_PIX_FMT_RGBX555:
1316 		alpha = 0;
1317 		/* fall through */
1318 	case V4L2_PIX_FMT_RGBA555:
1319 		buf[0][offset] = (g_u_s << 6) | (b_v << 1) |
1320 				 ((alpha & 0x80) >> 7);
1321 		buf[0][offset + 1] = (r_y_h << 3) | (g_u_s >> 2);
1322 		break;
1323 	case V4L2_PIX_FMT_XBGR555:
1324 		alpha = 0;
1325 		/* fall through */
1326 	case V4L2_PIX_FMT_ABGR555:
1327 		buf[0][offset] = (g_u_s << 5) | r_y_h;
1328 		buf[0][offset + 1] = (alpha & 0x80) | (b_v << 2)
1329 						    | (g_u_s >> 3);
1330 		break;
1331 	case V4L2_PIX_FMT_BGRX555:
1332 		alpha = 0;
1333 		/* fall through */
1334 	case V4L2_PIX_FMT_BGRA555:
1335 		buf[0][offset] = (g_u_s << 6) | (r_y_h << 1) |
1336 				 ((alpha & 0x80) >> 7);
1337 		buf[0][offset + 1] = (b_v << 3) | (g_u_s >> 2);
1338 		break;
1339 	case V4L2_PIX_FMT_RGB555X:
1340 	case V4L2_PIX_FMT_XRGB555X:
1341 		alpha = 0;
1342 		/* fall through */
1343 	case V4L2_PIX_FMT_ARGB555X:
1344 		buf[0][offset] = (alpha & 0x80) | (r_y_h << 2) | (g_u_s >> 3);
1345 		buf[0][offset + 1] = (g_u_s << 5) | b_v;
1346 		break;
1347 	case V4L2_PIX_FMT_RGB24:
1348 	case V4L2_PIX_FMT_HSV24:
1349 		buf[0][offset] = r_y_h;
1350 		buf[0][offset + 1] = g_u_s;
1351 		buf[0][offset + 2] = b_v;
1352 		break;
1353 	case V4L2_PIX_FMT_BGR24:
1354 		buf[0][offset] = b_v;
1355 		buf[0][offset + 1] = g_u_s;
1356 		buf[0][offset + 2] = r_y_h;
1357 		break;
1358 	case V4L2_PIX_FMT_BGR666:
1359 		buf[0][offset] = (b_v << 2) | (g_u_s >> 4);
1360 		buf[0][offset + 1] = (g_u_s << 4) | (r_y_h >> 2);
1361 		buf[0][offset + 2] = r_y_h << 6;
1362 		buf[0][offset + 3] = 0;
1363 		break;
1364 	case V4L2_PIX_FMT_RGB32:
1365 	case V4L2_PIX_FMT_XRGB32:
1366 	case V4L2_PIX_FMT_HSV32:
1367 	case V4L2_PIX_FMT_XYUV32:
1368 		alpha = 0;
1369 		/* fall through */
1370 	case V4L2_PIX_FMT_YUV32:
1371 	case V4L2_PIX_FMT_ARGB32:
1372 	case V4L2_PIX_FMT_AYUV32:
1373 		buf[0][offset] = alpha;
1374 		buf[0][offset + 1] = r_y_h;
1375 		buf[0][offset + 2] = g_u_s;
1376 		buf[0][offset + 3] = b_v;
1377 		break;
1378 	case V4L2_PIX_FMT_RGBX32:
1379 		alpha = 0;
1380 		/* fall through */
1381 	case V4L2_PIX_FMT_RGBA32:
1382 		buf[0][offset] = r_y_h;
1383 		buf[0][offset + 1] = g_u_s;
1384 		buf[0][offset + 2] = b_v;
1385 		buf[0][offset + 3] = alpha;
1386 		break;
1387 	case V4L2_PIX_FMT_BGR32:
1388 	case V4L2_PIX_FMT_XBGR32:
1389 	case V4L2_PIX_FMT_VUYX32:
1390 		alpha = 0;
1391 		/* fall through */
1392 	case V4L2_PIX_FMT_ABGR32:
1393 	case V4L2_PIX_FMT_VUYA32:
1394 		buf[0][offset] = b_v;
1395 		buf[0][offset + 1] = g_u_s;
1396 		buf[0][offset + 2] = r_y_h;
1397 		buf[0][offset + 3] = alpha;
1398 		break;
1399 	case V4L2_PIX_FMT_BGRX32:
1400 		alpha = 0;
1401 		/* fall through */
1402 	case V4L2_PIX_FMT_BGRA32:
1403 		buf[0][offset] = alpha;
1404 		buf[0][offset + 1] = b_v;
1405 		buf[0][offset + 2] = g_u_s;
1406 		buf[0][offset + 3] = r_y_h;
1407 		break;
1408 	case V4L2_PIX_FMT_SBGGR8:
1409 		buf[0][offset] = odd ? g_u_s : b_v;
1410 		buf[1][offset] = odd ? r_y_h : g_u_s;
1411 		break;
1412 	case V4L2_PIX_FMT_SGBRG8:
1413 		buf[0][offset] = odd ? b_v : g_u_s;
1414 		buf[1][offset] = odd ? g_u_s : r_y_h;
1415 		break;
1416 	case V4L2_PIX_FMT_SGRBG8:
1417 		buf[0][offset] = odd ? r_y_h : g_u_s;
1418 		buf[1][offset] = odd ? g_u_s : b_v;
1419 		break;
1420 	case V4L2_PIX_FMT_SRGGB8:
1421 		buf[0][offset] = odd ? g_u_s : r_y_h;
1422 		buf[1][offset] = odd ? b_v : g_u_s;
1423 		break;
1424 	case V4L2_PIX_FMT_SBGGR10:
1425 		buf[0][offset] = odd ? g_u_s << 2 : b_v << 2;
1426 		buf[0][offset + 1] = odd ? g_u_s >> 6 : b_v >> 6;
1427 		buf[1][offset] = odd ? r_y_h << 2 : g_u_s << 2;
1428 		buf[1][offset + 1] = odd ? r_y_h >> 6 : g_u_s >> 6;
1429 		buf[0][offset] |= (buf[0][offset] >> 2) & 3;
1430 		buf[1][offset] |= (buf[1][offset] >> 2) & 3;
1431 		break;
1432 	case V4L2_PIX_FMT_SGBRG10:
1433 		buf[0][offset] = odd ? b_v << 2 : g_u_s << 2;
1434 		buf[0][offset + 1] = odd ? b_v >> 6 : g_u_s >> 6;
1435 		buf[1][offset] = odd ? g_u_s << 2 : r_y_h << 2;
1436 		buf[1][offset + 1] = odd ? g_u_s >> 6 : r_y_h >> 6;
1437 		buf[0][offset] |= (buf[0][offset] >> 2) & 3;
1438 		buf[1][offset] |= (buf[1][offset] >> 2) & 3;
1439 		break;
1440 	case V4L2_PIX_FMT_SGRBG10:
1441 		buf[0][offset] = odd ? r_y_h << 2 : g_u_s << 2;
1442 		buf[0][offset + 1] = odd ? r_y_h >> 6 : g_u_s >> 6;
1443 		buf[1][offset] = odd ? g_u_s << 2 : b_v << 2;
1444 		buf[1][offset + 1] = odd ? g_u_s >> 6 : b_v >> 6;
1445 		buf[0][offset] |= (buf[0][offset] >> 2) & 3;
1446 		buf[1][offset] |= (buf[1][offset] >> 2) & 3;
1447 		break;
1448 	case V4L2_PIX_FMT_SRGGB10:
1449 		buf[0][offset] = odd ? g_u_s << 2 : r_y_h << 2;
1450 		buf[0][offset + 1] = odd ? g_u_s >> 6 : r_y_h >> 6;
1451 		buf[1][offset] = odd ? b_v << 2 : g_u_s << 2;
1452 		buf[1][offset + 1] = odd ? b_v >> 6 : g_u_s >> 6;
1453 		buf[0][offset] |= (buf[0][offset] >> 2) & 3;
1454 		buf[1][offset] |= (buf[1][offset] >> 2) & 3;
1455 		break;
1456 	case V4L2_PIX_FMT_SBGGR12:
1457 		buf[0][offset] = odd ? g_u_s << 4 : b_v << 4;
1458 		buf[0][offset + 1] = odd ? g_u_s >> 4 : b_v >> 4;
1459 		buf[1][offset] = odd ? r_y_h << 4 : g_u_s << 4;
1460 		buf[1][offset + 1] = odd ? r_y_h >> 4 : g_u_s >> 4;
1461 		buf[0][offset] |= (buf[0][offset] >> 4) & 0xf;
1462 		buf[1][offset] |= (buf[1][offset] >> 4) & 0xf;
1463 		break;
1464 	case V4L2_PIX_FMT_SGBRG12:
1465 		buf[0][offset] = odd ? b_v << 4 : g_u_s << 4;
1466 		buf[0][offset + 1] = odd ? b_v >> 4 : g_u_s >> 4;
1467 		buf[1][offset] = odd ? g_u_s << 4 : r_y_h << 4;
1468 		buf[1][offset + 1] = odd ? g_u_s >> 4 : r_y_h >> 4;
1469 		buf[0][offset] |= (buf[0][offset] >> 4) & 0xf;
1470 		buf[1][offset] |= (buf[1][offset] >> 4) & 0xf;
1471 		break;
1472 	case V4L2_PIX_FMT_SGRBG12:
1473 		buf[0][offset] = odd ? r_y_h << 4 : g_u_s << 4;
1474 		buf[0][offset + 1] = odd ? r_y_h >> 4 : g_u_s >> 4;
1475 		buf[1][offset] = odd ? g_u_s << 4 : b_v << 4;
1476 		buf[1][offset + 1] = odd ? g_u_s >> 4 : b_v >> 4;
1477 		buf[0][offset] |= (buf[0][offset] >> 4) & 0xf;
1478 		buf[1][offset] |= (buf[1][offset] >> 4) & 0xf;
1479 		break;
1480 	case V4L2_PIX_FMT_SRGGB12:
1481 		buf[0][offset] = odd ? g_u_s << 4 : r_y_h << 4;
1482 		buf[0][offset + 1] = odd ? g_u_s >> 4 : r_y_h >> 4;
1483 		buf[1][offset] = odd ? b_v << 4 : g_u_s << 4;
1484 		buf[1][offset + 1] = odd ? b_v >> 4 : g_u_s >> 4;
1485 		buf[0][offset] |= (buf[0][offset] >> 4) & 0xf;
1486 		buf[1][offset] |= (buf[1][offset] >> 4) & 0xf;
1487 		break;
1488 	case V4L2_PIX_FMT_SBGGR16:
1489 		buf[0][offset] = buf[0][offset + 1] = odd ? g_u_s : b_v;
1490 		buf[1][offset] = buf[1][offset + 1] = odd ? r_y_h : g_u_s;
1491 		break;
1492 	case V4L2_PIX_FMT_SGBRG16:
1493 		buf[0][offset] = buf[0][offset + 1] = odd ? b_v : g_u_s;
1494 		buf[1][offset] = buf[1][offset + 1] = odd ? g_u_s : r_y_h;
1495 		break;
1496 	case V4L2_PIX_FMT_SGRBG16:
1497 		buf[0][offset] = buf[0][offset + 1] = odd ? r_y_h : g_u_s;
1498 		buf[1][offset] = buf[1][offset + 1] = odd ? g_u_s : b_v;
1499 		break;
1500 	case V4L2_PIX_FMT_SRGGB16:
1501 		buf[0][offset] = buf[0][offset + 1] = odd ? g_u_s : r_y_h;
1502 		buf[1][offset] = buf[1][offset + 1] = odd ? b_v : g_u_s;
1503 		break;
1504 	}
1505 }
1506 
1507 unsigned tpg_g_interleaved_plane(const struct tpg_data *tpg, unsigned buf_line)
1508 {
1509 	switch (tpg->fourcc) {
1510 	case V4L2_PIX_FMT_SBGGR8:
1511 	case V4L2_PIX_FMT_SGBRG8:
1512 	case V4L2_PIX_FMT_SGRBG8:
1513 	case V4L2_PIX_FMT_SRGGB8:
1514 	case V4L2_PIX_FMT_SBGGR10:
1515 	case V4L2_PIX_FMT_SGBRG10:
1516 	case V4L2_PIX_FMT_SGRBG10:
1517 	case V4L2_PIX_FMT_SRGGB10:
1518 	case V4L2_PIX_FMT_SBGGR12:
1519 	case V4L2_PIX_FMT_SGBRG12:
1520 	case V4L2_PIX_FMT_SGRBG12:
1521 	case V4L2_PIX_FMT_SRGGB12:
1522 	case V4L2_PIX_FMT_SBGGR16:
1523 	case V4L2_PIX_FMT_SGBRG16:
1524 	case V4L2_PIX_FMT_SGRBG16:
1525 	case V4L2_PIX_FMT_SRGGB16:
1526 		return buf_line & 1;
1527 	default:
1528 		return 0;
1529 	}
1530 }
1531 EXPORT_SYMBOL_GPL(tpg_g_interleaved_plane);
1532 
1533 /* Return how many pattern lines are used by the current pattern. */
1534 static unsigned tpg_get_pat_lines(const struct tpg_data *tpg)
1535 {
1536 	switch (tpg->pattern) {
1537 	case TPG_PAT_CHECKERS_16X16:
1538 	case TPG_PAT_CHECKERS_2X2:
1539 	case TPG_PAT_CHECKERS_1X1:
1540 	case TPG_PAT_COLOR_CHECKERS_2X2:
1541 	case TPG_PAT_COLOR_CHECKERS_1X1:
1542 	case TPG_PAT_ALTERNATING_HLINES:
1543 	case TPG_PAT_CROSS_1_PIXEL:
1544 	case TPG_PAT_CROSS_2_PIXELS:
1545 	case TPG_PAT_CROSS_10_PIXELS:
1546 		return 2;
1547 	case TPG_PAT_100_COLORSQUARES:
1548 	case TPG_PAT_100_HCOLORBAR:
1549 		return 8;
1550 	default:
1551 		return 1;
1552 	}
1553 }
1554 
1555 /* Which pattern line should be used for the given frame line. */
1556 static unsigned tpg_get_pat_line(const struct tpg_data *tpg, unsigned line)
1557 {
1558 	switch (tpg->pattern) {
1559 	case TPG_PAT_CHECKERS_16X16:
1560 		return (line >> 4) & 1;
1561 	case TPG_PAT_CHECKERS_1X1:
1562 	case TPG_PAT_COLOR_CHECKERS_1X1:
1563 	case TPG_PAT_ALTERNATING_HLINES:
1564 		return line & 1;
1565 	case TPG_PAT_CHECKERS_2X2:
1566 	case TPG_PAT_COLOR_CHECKERS_2X2:
1567 		return (line & 2) >> 1;
1568 	case TPG_PAT_100_COLORSQUARES:
1569 	case TPG_PAT_100_HCOLORBAR:
1570 		return (line * 8) / tpg->src_height;
1571 	case TPG_PAT_CROSS_1_PIXEL:
1572 		return line == tpg->src_height / 2;
1573 	case TPG_PAT_CROSS_2_PIXELS:
1574 		return (line + 1) / 2 == tpg->src_height / 4;
1575 	case TPG_PAT_CROSS_10_PIXELS:
1576 		return (line + 10) / 20 == tpg->src_height / 40;
1577 	default:
1578 		return 0;
1579 	}
1580 }
1581 
1582 /*
1583  * Which color should be used for the given pattern line and X coordinate.
1584  * Note: x is in the range 0 to 2 * tpg->src_width.
1585  */
1586 static enum tpg_color tpg_get_color(const struct tpg_data *tpg,
1587 				    unsigned pat_line, unsigned x)
1588 {
1589 	/* Maximum number of bars are TPG_COLOR_MAX - otherwise, the input print code
1590 	   should be modified */
1591 	static const enum tpg_color bars[3][8] = {
1592 		/* Standard ITU-R 75% color bar sequence */
1593 		{ TPG_COLOR_CSC_WHITE,   TPG_COLOR_75_YELLOW,
1594 		  TPG_COLOR_75_CYAN,     TPG_COLOR_75_GREEN,
1595 		  TPG_COLOR_75_MAGENTA,  TPG_COLOR_75_RED,
1596 		  TPG_COLOR_75_BLUE,     TPG_COLOR_100_BLACK, },
1597 		/* Standard ITU-R 100% color bar sequence */
1598 		{ TPG_COLOR_100_WHITE,   TPG_COLOR_100_YELLOW,
1599 		  TPG_COLOR_100_CYAN,    TPG_COLOR_100_GREEN,
1600 		  TPG_COLOR_100_MAGENTA, TPG_COLOR_100_RED,
1601 		  TPG_COLOR_100_BLUE,    TPG_COLOR_100_BLACK, },
1602 		/* Color bar sequence suitable to test CSC */
1603 		{ TPG_COLOR_CSC_WHITE,   TPG_COLOR_CSC_YELLOW,
1604 		  TPG_COLOR_CSC_CYAN,    TPG_COLOR_CSC_GREEN,
1605 		  TPG_COLOR_CSC_MAGENTA, TPG_COLOR_CSC_RED,
1606 		  TPG_COLOR_CSC_BLUE,    TPG_COLOR_CSC_BLACK, },
1607 	};
1608 
1609 	switch (tpg->pattern) {
1610 	case TPG_PAT_75_COLORBAR:
1611 	case TPG_PAT_100_COLORBAR:
1612 	case TPG_PAT_CSC_COLORBAR:
1613 		return bars[tpg->pattern][((x * 8) / tpg->src_width) % 8];
1614 	case TPG_PAT_100_COLORSQUARES:
1615 		return bars[1][(pat_line + (x * 8) / tpg->src_width) % 8];
1616 	case TPG_PAT_100_HCOLORBAR:
1617 		return bars[1][pat_line];
1618 	case TPG_PAT_BLACK:
1619 		return TPG_COLOR_100_BLACK;
1620 	case TPG_PAT_WHITE:
1621 		return TPG_COLOR_100_WHITE;
1622 	case TPG_PAT_RED:
1623 		return TPG_COLOR_100_RED;
1624 	case TPG_PAT_GREEN:
1625 		return TPG_COLOR_100_GREEN;
1626 	case TPG_PAT_BLUE:
1627 		return TPG_COLOR_100_BLUE;
1628 	case TPG_PAT_CHECKERS_16X16:
1629 		return (((x >> 4) & 1) ^ (pat_line & 1)) ?
1630 			TPG_COLOR_100_BLACK : TPG_COLOR_100_WHITE;
1631 	case TPG_PAT_CHECKERS_1X1:
1632 		return ((x & 1) ^ (pat_line & 1)) ?
1633 			TPG_COLOR_100_WHITE : TPG_COLOR_100_BLACK;
1634 	case TPG_PAT_COLOR_CHECKERS_1X1:
1635 		return ((x & 1) ^ (pat_line & 1)) ?
1636 			TPG_COLOR_100_RED : TPG_COLOR_100_BLUE;
1637 	case TPG_PAT_CHECKERS_2X2:
1638 		return (((x >> 1) & 1) ^ (pat_line & 1)) ?
1639 			TPG_COLOR_100_WHITE : TPG_COLOR_100_BLACK;
1640 	case TPG_PAT_COLOR_CHECKERS_2X2:
1641 		return (((x >> 1) & 1) ^ (pat_line & 1)) ?
1642 			TPG_COLOR_100_RED : TPG_COLOR_100_BLUE;
1643 	case TPG_PAT_ALTERNATING_HLINES:
1644 		return pat_line ? TPG_COLOR_100_WHITE : TPG_COLOR_100_BLACK;
1645 	case TPG_PAT_ALTERNATING_VLINES:
1646 		return (x & 1) ? TPG_COLOR_100_WHITE : TPG_COLOR_100_BLACK;
1647 	case TPG_PAT_CROSS_1_PIXEL:
1648 		if (pat_line || (x % tpg->src_width) == tpg->src_width / 2)
1649 			return TPG_COLOR_100_BLACK;
1650 		return TPG_COLOR_100_WHITE;
1651 	case TPG_PAT_CROSS_2_PIXELS:
1652 		if (pat_line || ((x % tpg->src_width) + 1) / 2 == tpg->src_width / 4)
1653 			return TPG_COLOR_100_BLACK;
1654 		return TPG_COLOR_100_WHITE;
1655 	case TPG_PAT_CROSS_10_PIXELS:
1656 		if (pat_line || ((x % tpg->src_width) + 10) / 20 == tpg->src_width / 40)
1657 			return TPG_COLOR_100_BLACK;
1658 		return TPG_COLOR_100_WHITE;
1659 	case TPG_PAT_GRAY_RAMP:
1660 		return TPG_COLOR_RAMP + ((x % tpg->src_width) * 256) / tpg->src_width;
1661 	default:
1662 		return TPG_COLOR_100_RED;
1663 	}
1664 }
1665 
1666 /*
1667  * Given the pixel aspect ratio and video aspect ratio calculate the
1668  * coordinates of a centered square and the coordinates of the border of
1669  * the active video area. The coordinates are relative to the source
1670  * frame rectangle.
1671  */
1672 static void tpg_calculate_square_border(struct tpg_data *tpg)
1673 {
1674 	unsigned w = tpg->src_width;
1675 	unsigned h = tpg->src_height;
1676 	unsigned sq_w, sq_h;
1677 
1678 	sq_w = (w * 2 / 5) & ~1;
1679 	if (((w - sq_w) / 2) & 1)
1680 		sq_w += 2;
1681 	sq_h = sq_w;
1682 	tpg->square.width = sq_w;
1683 	if (tpg->vid_aspect == TPG_VIDEO_ASPECT_16X9_ANAMORPHIC) {
1684 		unsigned ana_sq_w = (sq_w / 4) * 3;
1685 
1686 		if (((w - ana_sq_w) / 2) & 1)
1687 			ana_sq_w += 2;
1688 		tpg->square.width = ana_sq_w;
1689 	}
1690 	tpg->square.left = (w - tpg->square.width) / 2;
1691 	if (tpg->pix_aspect == TPG_PIXEL_ASPECT_NTSC)
1692 		sq_h = sq_w * 10 / 11;
1693 	else if (tpg->pix_aspect == TPG_PIXEL_ASPECT_PAL)
1694 		sq_h = sq_w * 59 / 54;
1695 	tpg->square.height = sq_h;
1696 	tpg->square.top = (h - sq_h) / 2;
1697 	tpg->border.left = 0;
1698 	tpg->border.width = w;
1699 	tpg->border.top = 0;
1700 	tpg->border.height = h;
1701 	switch (tpg->vid_aspect) {
1702 	case TPG_VIDEO_ASPECT_4X3:
1703 		if (tpg->pix_aspect)
1704 			return;
1705 		if (3 * w >= 4 * h) {
1706 			tpg->border.width = ((4 * h) / 3) & ~1;
1707 			if (((w - tpg->border.width) / 2) & ~1)
1708 				tpg->border.width -= 2;
1709 			tpg->border.left = (w - tpg->border.width) / 2;
1710 			break;
1711 		}
1712 		tpg->border.height = ((3 * w) / 4) & ~1;
1713 		tpg->border.top = (h - tpg->border.height) / 2;
1714 		break;
1715 	case TPG_VIDEO_ASPECT_14X9_CENTRE:
1716 		if (tpg->pix_aspect) {
1717 			tpg->border.height = tpg->pix_aspect == TPG_PIXEL_ASPECT_NTSC ? 420 : 506;
1718 			tpg->border.top = (h - tpg->border.height) / 2;
1719 			break;
1720 		}
1721 		if (9 * w >= 14 * h) {
1722 			tpg->border.width = ((14 * h) / 9) & ~1;
1723 			if (((w - tpg->border.width) / 2) & ~1)
1724 				tpg->border.width -= 2;
1725 			tpg->border.left = (w - tpg->border.width) / 2;
1726 			break;
1727 		}
1728 		tpg->border.height = ((9 * w) / 14) & ~1;
1729 		tpg->border.top = (h - tpg->border.height) / 2;
1730 		break;
1731 	case TPG_VIDEO_ASPECT_16X9_CENTRE:
1732 		if (tpg->pix_aspect) {
1733 			tpg->border.height = tpg->pix_aspect == TPG_PIXEL_ASPECT_NTSC ? 368 : 442;
1734 			tpg->border.top = (h - tpg->border.height) / 2;
1735 			break;
1736 		}
1737 		if (9 * w >= 16 * h) {
1738 			tpg->border.width = ((16 * h) / 9) & ~1;
1739 			if (((w - tpg->border.width) / 2) & ~1)
1740 				tpg->border.width -= 2;
1741 			tpg->border.left = (w - tpg->border.width) / 2;
1742 			break;
1743 		}
1744 		tpg->border.height = ((9 * w) / 16) & ~1;
1745 		tpg->border.top = (h - tpg->border.height) / 2;
1746 		break;
1747 	default:
1748 		break;
1749 	}
1750 }
1751 
1752 static void tpg_precalculate_line(struct tpg_data *tpg)
1753 {
1754 	enum tpg_color contrast;
1755 	u8 pix[TPG_MAX_PLANES][8];
1756 	unsigned pat;
1757 	unsigned p;
1758 	unsigned x;
1759 
1760 	switch (tpg->pattern) {
1761 	case TPG_PAT_GREEN:
1762 		contrast = TPG_COLOR_100_RED;
1763 		break;
1764 	case TPG_PAT_CSC_COLORBAR:
1765 		contrast = TPG_COLOR_CSC_GREEN;
1766 		break;
1767 	default:
1768 		contrast = TPG_COLOR_100_GREEN;
1769 		break;
1770 	}
1771 
1772 	for (pat = 0; pat < tpg_get_pat_lines(tpg); pat++) {
1773 		/* Coarse scaling with Bresenham */
1774 		unsigned int_part = tpg->src_width / tpg->scaled_width;
1775 		unsigned fract_part = tpg->src_width % tpg->scaled_width;
1776 		unsigned src_x = 0;
1777 		unsigned error = 0;
1778 
1779 		for (x = 0; x < tpg->scaled_width * 2; x += 2) {
1780 			unsigned real_x = src_x;
1781 			enum tpg_color color1, color2;
1782 
1783 			real_x = tpg->hflip ? tpg->src_width * 2 - real_x - 2 : real_x;
1784 			color1 = tpg_get_color(tpg, pat, real_x);
1785 
1786 			src_x += int_part;
1787 			error += fract_part;
1788 			if (error >= tpg->scaled_width) {
1789 				error -= tpg->scaled_width;
1790 				src_x++;
1791 			}
1792 
1793 			real_x = src_x;
1794 			real_x = tpg->hflip ? tpg->src_width * 2 - real_x - 2 : real_x;
1795 			color2 = tpg_get_color(tpg, pat, real_x);
1796 
1797 			src_x += int_part;
1798 			error += fract_part;
1799 			if (error >= tpg->scaled_width) {
1800 				error -= tpg->scaled_width;
1801 				src_x++;
1802 			}
1803 
1804 			gen_twopix(tpg, pix, tpg->hflip ? color2 : color1, 0);
1805 			gen_twopix(tpg, pix, tpg->hflip ? color1 : color2, 1);
1806 			for (p = 0; p < tpg->planes; p++) {
1807 				unsigned twopixsize = tpg->twopixelsize[p];
1808 				unsigned hdiv = tpg->hdownsampling[p];
1809 				u8 *pos = tpg->lines[pat][p] + tpg_hdiv(tpg, p, x);
1810 
1811 				memcpy(pos, pix[p], twopixsize / hdiv);
1812 			}
1813 		}
1814 	}
1815 
1816 	if (tpg->vdownsampling[tpg->planes - 1] > 1) {
1817 		unsigned pat_lines = tpg_get_pat_lines(tpg);
1818 
1819 		for (pat = 0; pat < pat_lines; pat++) {
1820 			unsigned next_pat = (pat + 1) % pat_lines;
1821 
1822 			for (p = 1; p < tpg->planes; p++) {
1823 				unsigned w = tpg_hdiv(tpg, p, tpg->scaled_width * 2);
1824 				u8 *pos1 = tpg->lines[pat][p];
1825 				u8 *pos2 = tpg->lines[next_pat][p];
1826 				u8 *dest = tpg->downsampled_lines[pat][p];
1827 
1828 				for (x = 0; x < w; x++, pos1++, pos2++, dest++)
1829 					*dest = ((u16)*pos1 + (u16)*pos2) / 2;
1830 			}
1831 		}
1832 	}
1833 
1834 	gen_twopix(tpg, pix, contrast, 0);
1835 	gen_twopix(tpg, pix, contrast, 1);
1836 	for (p = 0; p < tpg->planes; p++) {
1837 		unsigned twopixsize = tpg->twopixelsize[p];
1838 		u8 *pos = tpg->contrast_line[p];
1839 
1840 		for (x = 0; x < tpg->scaled_width; x += 2, pos += twopixsize)
1841 			memcpy(pos, pix[p], twopixsize);
1842 	}
1843 
1844 	gen_twopix(tpg, pix, TPG_COLOR_100_BLACK, 0);
1845 	gen_twopix(tpg, pix, TPG_COLOR_100_BLACK, 1);
1846 	for (p = 0; p < tpg->planes; p++) {
1847 		unsigned twopixsize = tpg->twopixelsize[p];
1848 		u8 *pos = tpg->black_line[p];
1849 
1850 		for (x = 0; x < tpg->scaled_width; x += 2, pos += twopixsize)
1851 			memcpy(pos, pix[p], twopixsize);
1852 	}
1853 
1854 	for (x = 0; x < tpg->scaled_width * 2; x += 2) {
1855 		gen_twopix(tpg, pix, TPG_COLOR_RANDOM, 0);
1856 		gen_twopix(tpg, pix, TPG_COLOR_RANDOM, 1);
1857 		for (p = 0; p < tpg->planes; p++) {
1858 			unsigned twopixsize = tpg->twopixelsize[p];
1859 			u8 *pos = tpg->random_line[p] + x * twopixsize / 2;
1860 
1861 			memcpy(pos, pix[p], twopixsize);
1862 		}
1863 	}
1864 
1865 	gen_twopix(tpg, tpg->textbg, TPG_COLOR_TEXTBG, 0);
1866 	gen_twopix(tpg, tpg->textbg, TPG_COLOR_TEXTBG, 1);
1867 	gen_twopix(tpg, tpg->textfg, TPG_COLOR_TEXTFG, 0);
1868 	gen_twopix(tpg, tpg->textfg, TPG_COLOR_TEXTFG, 1);
1869 }
1870 
1871 /* need this to do rgb24 rendering */
1872 typedef struct { u16 __; u8 _; } __packed x24;
1873 
1874 #define PRINTSTR(PIXTYPE) do {	\
1875 	unsigned vdiv = tpg->vdownsampling[p]; \
1876 	unsigned hdiv = tpg->hdownsampling[p]; \
1877 	int line;	\
1878 	PIXTYPE fg;	\
1879 	PIXTYPE bg;	\
1880 	memcpy(&fg, tpg->textfg[p], sizeof(PIXTYPE));	\
1881 	memcpy(&bg, tpg->textbg[p], sizeof(PIXTYPE));	\
1882 	\
1883 	for (line = first; line < 16; line += vdiv * step) {	\
1884 		int l = tpg->vflip ? 15 - line : line; \
1885 		PIXTYPE *pos = (PIXTYPE *)(basep[p][(line / vdiv) & 1] + \
1886 			       ((y * step + l) / (vdiv * div)) * tpg->bytesperline[p] + \
1887 			       (x / hdiv) * sizeof(PIXTYPE));	\
1888 		unsigned s;	\
1889 	\
1890 		for (s = 0; s < len; s++) {	\
1891 			u8 chr = font8x16[(u8)text[s] * 16 + line];	\
1892 	\
1893 			if (hdiv == 2 && tpg->hflip) { \
1894 				pos[3] = (chr & (0x01 << 6) ? fg : bg);	\
1895 				pos[2] = (chr & (0x01 << 4) ? fg : bg);	\
1896 				pos[1] = (chr & (0x01 << 2) ? fg : bg);	\
1897 				pos[0] = (chr & (0x01 << 0) ? fg : bg);	\
1898 			} else if (hdiv == 2) { \
1899 				pos[0] = (chr & (0x01 << 7) ? fg : bg);	\
1900 				pos[1] = (chr & (0x01 << 5) ? fg : bg);	\
1901 				pos[2] = (chr & (0x01 << 3) ? fg : bg);	\
1902 				pos[3] = (chr & (0x01 << 1) ? fg : bg);	\
1903 			} else if (tpg->hflip) { \
1904 				pos[7] = (chr & (0x01 << 7) ? fg : bg);	\
1905 				pos[6] = (chr & (0x01 << 6) ? fg : bg);	\
1906 				pos[5] = (chr & (0x01 << 5) ? fg : bg);	\
1907 				pos[4] = (chr & (0x01 << 4) ? fg : bg);	\
1908 				pos[3] = (chr & (0x01 << 3) ? fg : bg);	\
1909 				pos[2] = (chr & (0x01 << 2) ? fg : bg);	\
1910 				pos[1] = (chr & (0x01 << 1) ? fg : bg);	\
1911 				pos[0] = (chr & (0x01 << 0) ? fg : bg);	\
1912 			} else { \
1913 				pos[0] = (chr & (0x01 << 7) ? fg : bg);	\
1914 				pos[1] = (chr & (0x01 << 6) ? fg : bg);	\
1915 				pos[2] = (chr & (0x01 << 5) ? fg : bg);	\
1916 				pos[3] = (chr & (0x01 << 4) ? fg : bg);	\
1917 				pos[4] = (chr & (0x01 << 3) ? fg : bg);	\
1918 				pos[5] = (chr & (0x01 << 2) ? fg : bg);	\
1919 				pos[6] = (chr & (0x01 << 1) ? fg : bg);	\
1920 				pos[7] = (chr & (0x01 << 0) ? fg : bg);	\
1921 			} \
1922 	\
1923 			pos += (tpg->hflip ? -8 : 8) / (int)hdiv;	\
1924 		}	\
1925 	}	\
1926 } while (0)
1927 
1928 static noinline void tpg_print_str_2(const struct tpg_data *tpg, u8 *basep[TPG_MAX_PLANES][2],
1929 			unsigned p, unsigned first, unsigned div, unsigned step,
1930 			int y, int x, char *text, unsigned len)
1931 {
1932 	PRINTSTR(u8);
1933 }
1934 
1935 static noinline void tpg_print_str_4(const struct tpg_data *tpg, u8 *basep[TPG_MAX_PLANES][2],
1936 			unsigned p, unsigned first, unsigned div, unsigned step,
1937 			int y, int x, char *text, unsigned len)
1938 {
1939 	PRINTSTR(u16);
1940 }
1941 
1942 static noinline void tpg_print_str_6(const struct tpg_data *tpg, u8 *basep[TPG_MAX_PLANES][2],
1943 			unsigned p, unsigned first, unsigned div, unsigned step,
1944 			int y, int x, char *text, unsigned len)
1945 {
1946 	PRINTSTR(x24);
1947 }
1948 
1949 static noinline void tpg_print_str_8(const struct tpg_data *tpg, u8 *basep[TPG_MAX_PLANES][2],
1950 			unsigned p, unsigned first, unsigned div, unsigned step,
1951 			int y, int x, char *text, unsigned len)
1952 {
1953 	PRINTSTR(u32);
1954 }
1955 
1956 void tpg_gen_text(const struct tpg_data *tpg, u8 *basep[TPG_MAX_PLANES][2],
1957 		  int y, int x, char *text)
1958 {
1959 	unsigned step = V4L2_FIELD_HAS_T_OR_B(tpg->field) ? 2 : 1;
1960 	unsigned div = step;
1961 	unsigned first = 0;
1962 	unsigned len = strlen(text);
1963 	unsigned p;
1964 
1965 	if (font8x16 == NULL || basep == NULL)
1966 		return;
1967 
1968 	/* Checks if it is possible to show string */
1969 	if (y + 16 >= tpg->compose.height || x + 8 >= tpg->compose.width)
1970 		return;
1971 
1972 	if (len > (tpg->compose.width - x) / 8)
1973 		len = (tpg->compose.width - x) / 8;
1974 	if (tpg->vflip)
1975 		y = tpg->compose.height - y - 16;
1976 	if (tpg->hflip)
1977 		x = tpg->compose.width - x - 8;
1978 	y += tpg->compose.top;
1979 	x += tpg->compose.left;
1980 	if (tpg->field == V4L2_FIELD_BOTTOM)
1981 		first = 1;
1982 	else if (tpg->field == V4L2_FIELD_SEQ_TB || tpg->field == V4L2_FIELD_SEQ_BT)
1983 		div = 2;
1984 
1985 	for (p = 0; p < tpg->planes; p++) {
1986 		/* Print text */
1987 		switch (tpg->twopixelsize[p]) {
1988 		case 2:
1989 			tpg_print_str_2(tpg, basep, p, first, div, step, y, x,
1990 					text, len);
1991 			break;
1992 		case 4:
1993 			tpg_print_str_4(tpg, basep, p, first, div, step, y, x,
1994 					text, len);
1995 			break;
1996 		case 6:
1997 			tpg_print_str_6(tpg, basep, p, first, div, step, y, x,
1998 					text, len);
1999 			break;
2000 		case 8:
2001 			tpg_print_str_8(tpg, basep, p, first, div, step, y, x,
2002 					text, len);
2003 			break;
2004 		}
2005 	}
2006 }
2007 EXPORT_SYMBOL_GPL(tpg_gen_text);
2008 
2009 void tpg_update_mv_step(struct tpg_data *tpg)
2010 {
2011 	int factor = tpg->mv_hor_mode > TPG_MOVE_NONE ? -1 : 1;
2012 
2013 	if (tpg->hflip)
2014 		factor = -factor;
2015 	switch (tpg->mv_hor_mode) {
2016 	case TPG_MOVE_NEG_FAST:
2017 	case TPG_MOVE_POS_FAST:
2018 		tpg->mv_hor_step = ((tpg->src_width + 319) / 320) * 4;
2019 		break;
2020 	case TPG_MOVE_NEG:
2021 	case TPG_MOVE_POS:
2022 		tpg->mv_hor_step = ((tpg->src_width + 639) / 640) * 4;
2023 		break;
2024 	case TPG_MOVE_NEG_SLOW:
2025 	case TPG_MOVE_POS_SLOW:
2026 		tpg->mv_hor_step = 2;
2027 		break;
2028 	case TPG_MOVE_NONE:
2029 		tpg->mv_hor_step = 0;
2030 		break;
2031 	}
2032 	if (factor < 0)
2033 		tpg->mv_hor_step = tpg->src_width - tpg->mv_hor_step;
2034 
2035 	factor = tpg->mv_vert_mode > TPG_MOVE_NONE ? -1 : 1;
2036 	switch (tpg->mv_vert_mode) {
2037 	case TPG_MOVE_NEG_FAST:
2038 	case TPG_MOVE_POS_FAST:
2039 		tpg->mv_vert_step = ((tpg->src_width + 319) / 320) * 4;
2040 		break;
2041 	case TPG_MOVE_NEG:
2042 	case TPG_MOVE_POS:
2043 		tpg->mv_vert_step = ((tpg->src_width + 639) / 640) * 4;
2044 		break;
2045 	case TPG_MOVE_NEG_SLOW:
2046 	case TPG_MOVE_POS_SLOW:
2047 		tpg->mv_vert_step = 1;
2048 		break;
2049 	case TPG_MOVE_NONE:
2050 		tpg->mv_vert_step = 0;
2051 		break;
2052 	}
2053 	if (factor < 0)
2054 		tpg->mv_vert_step = tpg->src_height - tpg->mv_vert_step;
2055 }
2056 EXPORT_SYMBOL_GPL(tpg_update_mv_step);
2057 
2058 /* Map the line number relative to the crop rectangle to a frame line number */
2059 static unsigned tpg_calc_frameline(const struct tpg_data *tpg, unsigned src_y,
2060 				    unsigned field)
2061 {
2062 	switch (field) {
2063 	case V4L2_FIELD_TOP:
2064 		return tpg->crop.top + src_y * 2;
2065 	case V4L2_FIELD_BOTTOM:
2066 		return tpg->crop.top + src_y * 2 + 1;
2067 	default:
2068 		return src_y + tpg->crop.top;
2069 	}
2070 }
2071 
2072 /*
2073  * Map the line number relative to the compose rectangle to a destination
2074  * buffer line number.
2075  */
2076 static unsigned tpg_calc_buffer_line(const struct tpg_data *tpg, unsigned y,
2077 				    unsigned field)
2078 {
2079 	y += tpg->compose.top;
2080 	switch (field) {
2081 	case V4L2_FIELD_SEQ_TB:
2082 		if (y & 1)
2083 			return tpg->buf_height / 2 + y / 2;
2084 		return y / 2;
2085 	case V4L2_FIELD_SEQ_BT:
2086 		if (y & 1)
2087 			return y / 2;
2088 		return tpg->buf_height / 2 + y / 2;
2089 	default:
2090 		return y;
2091 	}
2092 }
2093 
2094 static void tpg_recalc(struct tpg_data *tpg)
2095 {
2096 	if (tpg->recalc_colors) {
2097 		tpg->recalc_colors = false;
2098 		tpg->recalc_lines = true;
2099 		tpg->real_xfer_func = tpg->xfer_func;
2100 		tpg->real_ycbcr_enc = tpg->ycbcr_enc;
2101 		tpg->real_hsv_enc = tpg->hsv_enc;
2102 		tpg->real_quantization = tpg->quantization;
2103 
2104 		if (tpg->xfer_func == V4L2_XFER_FUNC_DEFAULT)
2105 			tpg->real_xfer_func =
2106 				V4L2_MAP_XFER_FUNC_DEFAULT(tpg->colorspace);
2107 
2108 		if (tpg->ycbcr_enc == V4L2_YCBCR_ENC_DEFAULT)
2109 			tpg->real_ycbcr_enc =
2110 				V4L2_MAP_YCBCR_ENC_DEFAULT(tpg->colorspace);
2111 
2112 		if (tpg->quantization == V4L2_QUANTIZATION_DEFAULT)
2113 			tpg->real_quantization =
2114 				V4L2_MAP_QUANTIZATION_DEFAULT(
2115 					tpg->color_enc != TGP_COLOR_ENC_YCBCR,
2116 					tpg->colorspace, tpg->real_ycbcr_enc);
2117 
2118 		tpg_precalculate_colors(tpg);
2119 	}
2120 	if (tpg->recalc_square_border) {
2121 		tpg->recalc_square_border = false;
2122 		tpg_calculate_square_border(tpg);
2123 	}
2124 	if (tpg->recalc_lines) {
2125 		tpg->recalc_lines = false;
2126 		tpg_precalculate_line(tpg);
2127 	}
2128 }
2129 
2130 void tpg_calc_text_basep(struct tpg_data *tpg,
2131 		u8 *basep[TPG_MAX_PLANES][2], unsigned p, u8 *vbuf)
2132 {
2133 	unsigned stride = tpg->bytesperline[p];
2134 	unsigned h = tpg->buf_height;
2135 
2136 	tpg_recalc(tpg);
2137 
2138 	basep[p][0] = vbuf;
2139 	basep[p][1] = vbuf;
2140 	h /= tpg->vdownsampling[p];
2141 	if (tpg->field == V4L2_FIELD_SEQ_TB)
2142 		basep[p][1] += h * stride / 2;
2143 	else if (tpg->field == V4L2_FIELD_SEQ_BT)
2144 		basep[p][0] += h * stride / 2;
2145 	if (p == 0 && tpg->interleaved)
2146 		tpg_calc_text_basep(tpg, basep, 1, vbuf);
2147 }
2148 EXPORT_SYMBOL_GPL(tpg_calc_text_basep);
2149 
2150 static int tpg_pattern_avg(const struct tpg_data *tpg,
2151 			   unsigned pat1, unsigned pat2)
2152 {
2153 	unsigned pat_lines = tpg_get_pat_lines(tpg);
2154 
2155 	if (pat1 == (pat2 + 1) % pat_lines)
2156 		return pat2;
2157 	if (pat2 == (pat1 + 1) % pat_lines)
2158 		return pat1;
2159 	return -1;
2160 }
2161 
2162 static const char *tpg_color_enc_str(enum tgp_color_enc
2163 						 color_enc)
2164 {
2165 	switch (color_enc) {
2166 	case TGP_COLOR_ENC_HSV:
2167 		return "HSV";
2168 	case TGP_COLOR_ENC_YCBCR:
2169 		return "Y'CbCr";
2170 	case TGP_COLOR_ENC_LUMA:
2171 		return "Luma";
2172 	case TGP_COLOR_ENC_RGB:
2173 	default:
2174 		return "R'G'B";
2175 
2176 	}
2177 }
2178 
2179 void tpg_log_status(struct tpg_data *tpg)
2180 {
2181 	pr_info("tpg source WxH: %ux%u (%s)\n",
2182 		tpg->src_width, tpg->src_height,
2183 		tpg_color_enc_str(tpg->color_enc));
2184 	pr_info("tpg field: %u\n", tpg->field);
2185 	pr_info("tpg crop: %ux%u@%dx%d\n", tpg->crop.width, tpg->crop.height,
2186 			tpg->crop.left, tpg->crop.top);
2187 	pr_info("tpg compose: %ux%u@%dx%d\n", tpg->compose.width, tpg->compose.height,
2188 			tpg->compose.left, tpg->compose.top);
2189 	pr_info("tpg colorspace: %d\n", tpg->colorspace);
2190 	pr_info("tpg transfer function: %d/%d\n", tpg->xfer_func, tpg->real_xfer_func);
2191 	if (tpg->color_enc == TGP_COLOR_ENC_HSV)
2192 		pr_info("tpg HSV encoding: %d/%d\n",
2193 			tpg->hsv_enc, tpg->real_hsv_enc);
2194 	else if (tpg->color_enc == TGP_COLOR_ENC_YCBCR)
2195 		pr_info("tpg Y'CbCr encoding: %d/%d\n",
2196 			tpg->ycbcr_enc, tpg->real_ycbcr_enc);
2197 	pr_info("tpg quantization: %d/%d\n", tpg->quantization, tpg->real_quantization);
2198 	pr_info("tpg RGB range: %d/%d\n", tpg->rgb_range, tpg->real_rgb_range);
2199 }
2200 EXPORT_SYMBOL_GPL(tpg_log_status);
2201 
2202 /*
2203  * This struct contains common parameters used by both the drawing of the
2204  * test pattern and the drawing of the extras (borders, square, etc.)
2205  */
2206 struct tpg_draw_params {
2207 	/* common data */
2208 	bool is_tv;
2209 	bool is_60hz;
2210 	unsigned twopixsize;
2211 	unsigned img_width;
2212 	unsigned stride;
2213 	unsigned hmax;
2214 	unsigned frame_line;
2215 	unsigned frame_line_next;
2216 
2217 	/* test pattern */
2218 	unsigned mv_hor_old;
2219 	unsigned mv_hor_new;
2220 	unsigned mv_vert_old;
2221 	unsigned mv_vert_new;
2222 
2223 	/* extras */
2224 	unsigned wss_width;
2225 	unsigned wss_random_offset;
2226 	unsigned sav_eav_f;
2227 	unsigned left_pillar_width;
2228 	unsigned right_pillar_start;
2229 };
2230 
2231 static void tpg_fill_params_pattern(const struct tpg_data *tpg, unsigned p,
2232 				    struct tpg_draw_params *params)
2233 {
2234 	params->mv_hor_old =
2235 		tpg_hscale_div(tpg, p, tpg->mv_hor_count % tpg->src_width);
2236 	params->mv_hor_new =
2237 		tpg_hscale_div(tpg, p, (tpg->mv_hor_count + tpg->mv_hor_step) %
2238 			       tpg->src_width);
2239 	params->mv_vert_old = tpg->mv_vert_count % tpg->src_height;
2240 	params->mv_vert_new =
2241 		(tpg->mv_vert_count + tpg->mv_vert_step) % tpg->src_height;
2242 }
2243 
2244 static void tpg_fill_params_extras(const struct tpg_data *tpg,
2245 				   unsigned p,
2246 				   struct tpg_draw_params *params)
2247 {
2248 	unsigned left_pillar_width = 0;
2249 	unsigned right_pillar_start = params->img_width;
2250 
2251 	params->wss_width = tpg->crop.left < tpg->src_width / 2 ?
2252 		tpg->src_width / 2 - tpg->crop.left : 0;
2253 	if (params->wss_width > tpg->crop.width)
2254 		params->wss_width = tpg->crop.width;
2255 	params->wss_width = tpg_hscale_div(tpg, p, params->wss_width);
2256 	params->wss_random_offset =
2257 		params->twopixsize * prandom_u32_max(tpg->src_width / 2);
2258 
2259 	if (tpg->crop.left < tpg->border.left) {
2260 		left_pillar_width = tpg->border.left - tpg->crop.left;
2261 		if (left_pillar_width > tpg->crop.width)
2262 			left_pillar_width = tpg->crop.width;
2263 		left_pillar_width = tpg_hscale_div(tpg, p, left_pillar_width);
2264 	}
2265 	params->left_pillar_width = left_pillar_width;
2266 
2267 	if (tpg->crop.left + tpg->crop.width >
2268 	    tpg->border.left + tpg->border.width) {
2269 		right_pillar_start =
2270 			tpg->border.left + tpg->border.width - tpg->crop.left;
2271 		right_pillar_start =
2272 			tpg_hscale_div(tpg, p, right_pillar_start);
2273 		if (right_pillar_start > params->img_width)
2274 			right_pillar_start = params->img_width;
2275 	}
2276 	params->right_pillar_start = right_pillar_start;
2277 
2278 	params->sav_eav_f = tpg->field ==
2279 			(params->is_60hz ? V4L2_FIELD_TOP : V4L2_FIELD_BOTTOM);
2280 }
2281 
2282 static void tpg_fill_plane_extras(const struct tpg_data *tpg,
2283 				  const struct tpg_draw_params *params,
2284 				  unsigned p, unsigned h, u8 *vbuf)
2285 {
2286 	unsigned twopixsize = params->twopixsize;
2287 	unsigned img_width = params->img_width;
2288 	unsigned frame_line = params->frame_line;
2289 	const struct v4l2_rect *sq = &tpg->square;
2290 	const struct v4l2_rect *b = &tpg->border;
2291 	const struct v4l2_rect *c = &tpg->crop;
2292 
2293 	if (params->is_tv && !params->is_60hz &&
2294 	    frame_line == 0 && params->wss_width) {
2295 		/*
2296 		 * Replace the first half of the top line of a 50 Hz frame
2297 		 * with random data to simulate a WSS signal.
2298 		 */
2299 		u8 *wss = tpg->random_line[p] + params->wss_random_offset;
2300 
2301 		memcpy(vbuf, wss, params->wss_width);
2302 	}
2303 
2304 	if (tpg->show_border && frame_line >= b->top &&
2305 	    frame_line < b->top + b->height) {
2306 		unsigned bottom = b->top + b->height - 1;
2307 		unsigned left = params->left_pillar_width;
2308 		unsigned right = params->right_pillar_start;
2309 
2310 		if (frame_line == b->top || frame_line == b->top + 1 ||
2311 		    frame_line == bottom || frame_line == bottom - 1) {
2312 			memcpy(vbuf + left, tpg->contrast_line[p],
2313 					right - left);
2314 		} else {
2315 			if (b->left >= c->left &&
2316 			    b->left < c->left + c->width)
2317 				memcpy(vbuf + left,
2318 					tpg->contrast_line[p], twopixsize);
2319 			if (b->left + b->width > c->left &&
2320 			    b->left + b->width <= c->left + c->width)
2321 				memcpy(vbuf + right - twopixsize,
2322 					tpg->contrast_line[p], twopixsize);
2323 		}
2324 	}
2325 	if (tpg->qual != TPG_QUAL_NOISE && frame_line >= b->top &&
2326 	    frame_line < b->top + b->height) {
2327 		memcpy(vbuf, tpg->black_line[p], params->left_pillar_width);
2328 		memcpy(vbuf + params->right_pillar_start, tpg->black_line[p],
2329 		       img_width - params->right_pillar_start);
2330 	}
2331 	if (tpg->show_square && frame_line >= sq->top &&
2332 	    frame_line < sq->top + sq->height &&
2333 	    sq->left < c->left + c->width &&
2334 	    sq->left + sq->width >= c->left) {
2335 		unsigned left = sq->left;
2336 		unsigned width = sq->width;
2337 
2338 		if (c->left > left) {
2339 			width -= c->left - left;
2340 			left = c->left;
2341 		}
2342 		if (c->left + c->width < left + width)
2343 			width -= left + width - c->left - c->width;
2344 		left -= c->left;
2345 		left = tpg_hscale_div(tpg, p, left);
2346 		width = tpg_hscale_div(tpg, p, width);
2347 		memcpy(vbuf + left, tpg->contrast_line[p], width);
2348 	}
2349 	if (tpg->insert_sav) {
2350 		unsigned offset = tpg_hdiv(tpg, p, tpg->compose.width / 3);
2351 		u8 *p = vbuf + offset;
2352 		unsigned vact = 0, hact = 0;
2353 
2354 		p[0] = 0xff;
2355 		p[1] = 0;
2356 		p[2] = 0;
2357 		p[3] = 0x80 | (params->sav_eav_f << 6) |
2358 			(vact << 5) | (hact << 4) |
2359 			((hact ^ vact) << 3) |
2360 			((hact ^ params->sav_eav_f) << 2) |
2361 			((params->sav_eav_f ^ vact) << 1) |
2362 			(hact ^ vact ^ params->sav_eav_f);
2363 	}
2364 	if (tpg->insert_eav) {
2365 		unsigned offset = tpg_hdiv(tpg, p, tpg->compose.width * 2 / 3);
2366 		u8 *p = vbuf + offset;
2367 		unsigned vact = 0, hact = 1;
2368 
2369 		p[0] = 0xff;
2370 		p[1] = 0;
2371 		p[2] = 0;
2372 		p[3] = 0x80 | (params->sav_eav_f << 6) |
2373 			(vact << 5) | (hact << 4) |
2374 			((hact ^ vact) << 3) |
2375 			((hact ^ params->sav_eav_f) << 2) |
2376 			((params->sav_eav_f ^ vact) << 1) |
2377 			(hact ^ vact ^ params->sav_eav_f);
2378 	}
2379 }
2380 
2381 static void tpg_fill_plane_pattern(const struct tpg_data *tpg,
2382 				   const struct tpg_draw_params *params,
2383 				   unsigned p, unsigned h, u8 *vbuf)
2384 {
2385 	unsigned twopixsize = params->twopixsize;
2386 	unsigned img_width = params->img_width;
2387 	unsigned mv_hor_old = params->mv_hor_old;
2388 	unsigned mv_hor_new = params->mv_hor_new;
2389 	unsigned mv_vert_old = params->mv_vert_old;
2390 	unsigned mv_vert_new = params->mv_vert_new;
2391 	unsigned frame_line = params->frame_line;
2392 	unsigned frame_line_next = params->frame_line_next;
2393 	unsigned line_offset = tpg_hscale_div(tpg, p, tpg->crop.left);
2394 	bool even;
2395 	bool fill_blank = false;
2396 	unsigned pat_line_old;
2397 	unsigned pat_line_new;
2398 	u8 *linestart_older;
2399 	u8 *linestart_newer;
2400 	u8 *linestart_top;
2401 	u8 *linestart_bottom;
2402 
2403 	even = !(frame_line & 1);
2404 
2405 	if (h >= params->hmax) {
2406 		if (params->hmax == tpg->compose.height)
2407 			return;
2408 		if (!tpg->perc_fill_blank)
2409 			return;
2410 		fill_blank = true;
2411 	}
2412 
2413 	if (tpg->vflip) {
2414 		frame_line = tpg->src_height - frame_line - 1;
2415 		frame_line_next = tpg->src_height - frame_line_next - 1;
2416 	}
2417 
2418 	if (fill_blank) {
2419 		linestart_older = tpg->contrast_line[p];
2420 		linestart_newer = tpg->contrast_line[p];
2421 	} else if (tpg->qual != TPG_QUAL_NOISE &&
2422 		   (frame_line < tpg->border.top ||
2423 		    frame_line >= tpg->border.top + tpg->border.height)) {
2424 		linestart_older = tpg->black_line[p];
2425 		linestart_newer = tpg->black_line[p];
2426 	} else if (tpg->pattern == TPG_PAT_NOISE || tpg->qual == TPG_QUAL_NOISE) {
2427 		linestart_older = tpg->random_line[p] +
2428 				  twopixsize * prandom_u32_max(tpg->src_width / 2);
2429 		linestart_newer = tpg->random_line[p] +
2430 				  twopixsize * prandom_u32_max(tpg->src_width / 2);
2431 	} else {
2432 		unsigned frame_line_old =
2433 			(frame_line + mv_vert_old) % tpg->src_height;
2434 		unsigned frame_line_new =
2435 			(frame_line + mv_vert_new) % tpg->src_height;
2436 		unsigned pat_line_next_old;
2437 		unsigned pat_line_next_new;
2438 
2439 		pat_line_old = tpg_get_pat_line(tpg, frame_line_old);
2440 		pat_line_new = tpg_get_pat_line(tpg, frame_line_new);
2441 		linestart_older = tpg->lines[pat_line_old][p] + mv_hor_old;
2442 		linestart_newer = tpg->lines[pat_line_new][p] + mv_hor_new;
2443 
2444 		if (tpg->vdownsampling[p] > 1 && frame_line != frame_line_next) {
2445 			int avg_pat;
2446 
2447 			/*
2448 			 * Now decide whether we need to use downsampled_lines[].
2449 			 * That's necessary if the two lines use different patterns.
2450 			 */
2451 			pat_line_next_old = tpg_get_pat_line(tpg,
2452 					(frame_line_next + mv_vert_old) % tpg->src_height);
2453 			pat_line_next_new = tpg_get_pat_line(tpg,
2454 					(frame_line_next + mv_vert_new) % tpg->src_height);
2455 
2456 			switch (tpg->field) {
2457 			case V4L2_FIELD_INTERLACED:
2458 			case V4L2_FIELD_INTERLACED_BT:
2459 			case V4L2_FIELD_INTERLACED_TB:
2460 				avg_pat = tpg_pattern_avg(tpg, pat_line_old, pat_line_new);
2461 				if (avg_pat < 0)
2462 					break;
2463 				linestart_older = tpg->downsampled_lines[avg_pat][p] + mv_hor_old;
2464 				linestart_newer = linestart_older;
2465 				break;
2466 			case V4L2_FIELD_NONE:
2467 			case V4L2_FIELD_TOP:
2468 			case V4L2_FIELD_BOTTOM:
2469 			case V4L2_FIELD_SEQ_BT:
2470 			case V4L2_FIELD_SEQ_TB:
2471 				avg_pat = tpg_pattern_avg(tpg, pat_line_old, pat_line_next_old);
2472 				if (avg_pat >= 0)
2473 					linestart_older = tpg->downsampled_lines[avg_pat][p] +
2474 						mv_hor_old;
2475 				avg_pat = tpg_pattern_avg(tpg, pat_line_new, pat_line_next_new);
2476 				if (avg_pat >= 0)
2477 					linestart_newer = tpg->downsampled_lines[avg_pat][p] +
2478 						mv_hor_new;
2479 				break;
2480 			}
2481 		}
2482 		linestart_older += line_offset;
2483 		linestart_newer += line_offset;
2484 	}
2485 	if (tpg->field_alternate) {
2486 		linestart_top = linestart_bottom = linestart_older;
2487 	} else if (params->is_60hz) {
2488 		linestart_top = linestart_newer;
2489 		linestart_bottom = linestart_older;
2490 	} else {
2491 		linestart_top = linestart_older;
2492 		linestart_bottom = linestart_newer;
2493 	}
2494 
2495 	switch (tpg->field) {
2496 	case V4L2_FIELD_INTERLACED:
2497 	case V4L2_FIELD_INTERLACED_TB:
2498 	case V4L2_FIELD_SEQ_TB:
2499 	case V4L2_FIELD_SEQ_BT:
2500 		if (even)
2501 			memcpy(vbuf, linestart_top, img_width);
2502 		else
2503 			memcpy(vbuf, linestart_bottom, img_width);
2504 		break;
2505 	case V4L2_FIELD_INTERLACED_BT:
2506 		if (even)
2507 			memcpy(vbuf, linestart_bottom, img_width);
2508 		else
2509 			memcpy(vbuf, linestart_top, img_width);
2510 		break;
2511 	case V4L2_FIELD_TOP:
2512 		memcpy(vbuf, linestart_top, img_width);
2513 		break;
2514 	case V4L2_FIELD_BOTTOM:
2515 		memcpy(vbuf, linestart_bottom, img_width);
2516 		break;
2517 	case V4L2_FIELD_NONE:
2518 	default:
2519 		memcpy(vbuf, linestart_older, img_width);
2520 		break;
2521 	}
2522 }
2523 
2524 void tpg_fill_plane_buffer(struct tpg_data *tpg, v4l2_std_id std,
2525 			   unsigned p, u8 *vbuf)
2526 {
2527 	struct tpg_draw_params params;
2528 	unsigned factor = V4L2_FIELD_HAS_T_OR_B(tpg->field) ? 2 : 1;
2529 
2530 	/* Coarse scaling with Bresenham */
2531 	unsigned int_part = (tpg->crop.height / factor) / tpg->compose.height;
2532 	unsigned fract_part = (tpg->crop.height / factor) % tpg->compose.height;
2533 	unsigned src_y = 0;
2534 	unsigned error = 0;
2535 	unsigned h;
2536 
2537 	tpg_recalc(tpg);
2538 
2539 	params.is_tv = std;
2540 	params.is_60hz = std & V4L2_STD_525_60;
2541 	params.twopixsize = tpg->twopixelsize[p];
2542 	params.img_width = tpg_hdiv(tpg, p, tpg->compose.width);
2543 	params.stride = tpg->bytesperline[p];
2544 	params.hmax = (tpg->compose.height * tpg->perc_fill) / 100;
2545 
2546 	tpg_fill_params_pattern(tpg, p, &params);
2547 	tpg_fill_params_extras(tpg, p, &params);
2548 
2549 	vbuf += tpg_hdiv(tpg, p, tpg->compose.left);
2550 
2551 	for (h = 0; h < tpg->compose.height; h++) {
2552 		unsigned buf_line;
2553 
2554 		params.frame_line = tpg_calc_frameline(tpg, src_y, tpg->field);
2555 		params.frame_line_next = params.frame_line;
2556 		buf_line = tpg_calc_buffer_line(tpg, h, tpg->field);
2557 		src_y += int_part;
2558 		error += fract_part;
2559 		if (error >= tpg->compose.height) {
2560 			error -= tpg->compose.height;
2561 			src_y++;
2562 		}
2563 
2564 		/*
2565 		 * For line-interleaved formats determine the 'plane'
2566 		 * based on the buffer line.
2567 		 */
2568 		if (tpg_g_interleaved(tpg))
2569 			p = tpg_g_interleaved_plane(tpg, buf_line);
2570 
2571 		if (tpg->vdownsampling[p] > 1) {
2572 			/*
2573 			 * When doing vertical downsampling the field setting
2574 			 * matters: for SEQ_BT/TB we downsample each field
2575 			 * separately (i.e. lines 0+2 are combined, as are
2576 			 * lines 1+3), for the other field settings we combine
2577 			 * odd and even lines. Doing that for SEQ_BT/TB would
2578 			 * be really weird.
2579 			 */
2580 			if (tpg->field == V4L2_FIELD_SEQ_BT ||
2581 			    tpg->field == V4L2_FIELD_SEQ_TB) {
2582 				unsigned next_src_y = src_y;
2583 
2584 				if ((h & 3) >= 2)
2585 					continue;
2586 				next_src_y += int_part;
2587 				if (error + fract_part >= tpg->compose.height)
2588 					next_src_y++;
2589 				params.frame_line_next =
2590 					tpg_calc_frameline(tpg, next_src_y, tpg->field);
2591 			} else {
2592 				if (h & 1)
2593 					continue;
2594 				params.frame_line_next =
2595 					tpg_calc_frameline(tpg, src_y, tpg->field);
2596 			}
2597 
2598 			buf_line /= tpg->vdownsampling[p];
2599 		}
2600 		tpg_fill_plane_pattern(tpg, &params, p, h,
2601 				vbuf + buf_line * params.stride);
2602 		tpg_fill_plane_extras(tpg, &params, p, h,
2603 				vbuf + buf_line * params.stride);
2604 	}
2605 }
2606 EXPORT_SYMBOL_GPL(tpg_fill_plane_buffer);
2607 
2608 void tpg_fillbuffer(struct tpg_data *tpg, v4l2_std_id std, unsigned p, u8 *vbuf)
2609 {
2610 	unsigned offset = 0;
2611 	unsigned i;
2612 
2613 	if (tpg->buffers > 1) {
2614 		tpg_fill_plane_buffer(tpg, std, p, vbuf);
2615 		return;
2616 	}
2617 
2618 	for (i = 0; i < tpg_g_planes(tpg); i++) {
2619 		tpg_fill_plane_buffer(tpg, std, i, vbuf + offset);
2620 		offset += tpg_calc_plane_size(tpg, i);
2621 	}
2622 }
2623 EXPORT_SYMBOL_GPL(tpg_fillbuffer);
2624 
2625 MODULE_DESCRIPTION("V4L2 Test Pattern Generator");
2626 MODULE_AUTHOR("Hans Verkuil");
2627 MODULE_LICENSE("GPL");
2628