blob: 19bd203f52983136e20268609b8c6f3407553c2f [file] [log] [blame]
codeworkxf1be2fe2012-03-24 17:38:29 +01001/*
2 *
3 * Copyright 2012 Samsung Electronics S.LSI Co. LTD
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 */
17
18/*
19 * @file csc.c
20 *
21 * @brief color space convertion abstract source
22 *
23 * @author Pyoungjae Jung(pjet.jung@samsung.com)
24 *
25 * @version 1.0.0
26 *
27 * @history
28 * 2012.1.11 : Create
29 */
30#define LOG_TAG "libcsc"
31#include <cutils/log.h>
32
33#include <stdio.h>
34#include <stdlib.h>
35#include <utils/Log.h>
36
37#include "csc.h"
38#include "sec_format.h"
39#include "sec_utils_v4l2.h"
40#include "swconverter.h"
41
42#ifdef EXYNOS_OMX
43#include "Exynos_OMX_Def.h"
44#else
45#include "SEC_OMX_Def.h"
46#endif
47
48#ifdef USE_FIMC
49#include "hwconverter_wrapper.h"
50#endif
51
52#ifdef USE_GSCALER
53#include "exynos_gscaler.h"
54#endif
55
56#define GSCALER_IMG_ALIGN 16
57#define CSC_MAX_PLANES 3
58#define ALIGN(x, a) (((x) + (a) - 1) & ~((a) - 1))
59
60typedef enum _CSC_PLANE {
61 CSC_Y_PLANE = 0,
62 CSC_RGB_PLANE = 0,
63 CSC_U_PLANE = 1,
64 CSC_UV_PLANE = 1,
65 CSC_V_PLANE = 2
66} CSC_PLANE;
67
68typedef enum _CSC_HW_TYPE {
69 CSC_HW_TYPE_FIMC = 0,
70 CSC_HW_TYPE_GSCALER
71} CSC_HW_TYPE;
72
73typedef struct _CSC_FORMAT {
74 unsigned int width;
75 unsigned int height;
76 unsigned int crop_left;
77 unsigned int crop_top;
78 unsigned int crop_width;
79 unsigned int crop_height;
80 unsigned int color_format;
81 unsigned int cacheable;
82} CSC_FORMAT;
83
84typedef struct _CSC_BUFFER {
85 unsigned char *planes[CSC_MAX_PLANES];
86 int ion_fd;
87} CSC_BUFFER;
88
89typedef struct _CSC_HANDLE {
90 CSC_FORMAT dst_format;
91 CSC_FORMAT src_format;
92 CSC_BUFFER dst_buffer;
93 CSC_BUFFER src_buffer;
94 CSC_METHOD csc_method;
95 CSC_HW_TYPE csc_hw_type;
96 void *csc_hw_handle;
97} CSC_HANDLE;
98
99OMX_COLOR_FORMATTYPE hal_2_omx_pixel_format(
100 unsigned int hal_format)
101{
102 OMX_COLOR_FORMATTYPE omx_format;
103 switch (hal_format) {
104 case HAL_PIXEL_FORMAT_YCbCr_420_P:
105 omx_format = OMX_COLOR_FormatYUV420Planar;
106 break;
107 case HAL_PIXEL_FORMAT_YCbCr_420_SP:
108 omx_format = OMX_COLOR_FormatYUV420SemiPlanar;
109 break;
110 case HAL_PIXEL_FORMAT_YCbCr_420_SP_TILED:
111 omx_format = OMX_SEC_COLOR_FormatNV12Tiled;
112 break;
113 case HAL_PIXEL_FORMAT_ARGB888:
114 omx_format = OMX_COLOR_Format32bitARGB8888;
115 break;
116 default:
117 omx_format = OMX_COLOR_FormatYUV420Planar;
118 break;
119 }
120 return omx_format;
121}
122
123unsigned int omx_2_hal_pixel_format(
124 OMX_COLOR_FORMATTYPE omx_format)
125{
126 unsigned int hal_format;
127 switch (omx_format) {
128 case OMX_COLOR_FormatYUV420Planar:
129 hal_format = HAL_PIXEL_FORMAT_YCbCr_420_P;
130 break;
131 case OMX_COLOR_FormatYUV420SemiPlanar:
132 hal_format = HAL_PIXEL_FORMAT_YCbCr_420_SP;
133 break;
134 case OMX_SEC_COLOR_FormatNV12Tiled:
135 hal_format = HAL_PIXEL_FORMAT_YCbCr_420_SP_TILED;
136 break;
137 case OMX_COLOR_Format32bitARGB8888:
138 hal_format = HAL_PIXEL_FORMAT_ARGB888;
139 break;
140 default:
141 hal_format = HAL_PIXEL_FORMAT_YCbCr_420_P;
142 break;
143 }
144 return hal_format;
145}
146
147/* source is RGB888 */
148static CSC_ERRORCODE conv_sw_src_argb888(
149 CSC_HANDLE *handle)
150{
151 CSC_ERRORCODE ret = CSC_ErrorNone;
152
153 switch (handle->dst_format.color_format) {
154 case HAL_PIXEL_FORMAT_YCbCr_420_P:
155 csc_ARGB8888_to_YUV420P(
156 (unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
157 (unsigned char *)handle->dst_buffer.planes[CSC_U_PLANE],
158 (unsigned char *)handle->dst_buffer.planes[CSC_V_PLANE],
159 (unsigned char *)handle->src_buffer.planes[CSC_RGB_PLANE],
160 handle->src_format.width,
161 handle->src_format.height);
162 ret = CSC_ErrorNone;
163 break;
164 case HAL_PIXEL_FORMAT_YCbCr_420_SP:
165 csc_ARGB8888_to_YUV420SP(
166 (unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
167 (unsigned char *)handle->dst_buffer.planes[CSC_UV_PLANE],
168 (unsigned char *)handle->src_buffer.planes[CSC_RGB_PLANE],
169 handle->src_format.width,
170 handle->src_format.height);
171 ret = CSC_ErrorNone;
172 break;
173 default:
174 ret = CSC_ErrorUnsupportFormat;
175 break;
176 }
177
178 return ret;
179}
180
181/* source is NV12T */
182static CSC_ERRORCODE conv_sw_src_nv12t(
183 CSC_HANDLE *handle)
184{
185 CSC_ERRORCODE ret = CSC_ErrorNone;
186
187 switch (handle->dst_format.color_format) {
188 case HAL_PIXEL_FORMAT_YCbCr_420_P:
189 csc_tiled_to_linear_y_neon(
190 (unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
191 (unsigned char *)handle->src_buffer.planes[CSC_Y_PLANE],
192 handle->src_format.width,
193 handle->src_format.height);
194 csc_tiled_to_linear_uv_deinterleave_neon(
195 (unsigned char *)handle->dst_buffer.planes[CSC_U_PLANE],
196 (unsigned char *)handle->dst_buffer.planes[CSC_V_PLANE],
197 (unsigned char *)handle->src_buffer.planes[CSC_UV_PLANE],
198 handle->src_format.width,
199 handle->src_format.height / 2);
200 ret = CSC_ErrorNone;
201 break;
202 case HAL_PIXEL_FORMAT_YCbCr_420_SP:
203 csc_tiled_to_linear_y_neon(
204 (unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
205 (unsigned char *)handle->src_buffer.planes[CSC_Y_PLANE],
206 handle->src_format.width,
207 handle->src_format.height);
208 csc_tiled_to_linear_uv_neon(
209 (unsigned char *)handle->dst_buffer.planes[CSC_UV_PLANE],
210 (unsigned char *)handle->src_buffer.planes[CSC_UV_PLANE],
211 handle->src_format.width,
212 handle->src_format.height / 2);
213 ret = CSC_ErrorNone;
214 break;
215 default:
216 ret = CSC_ErrorUnsupportFormat;
217 break;
218 }
219
220 return ret;
221}
222
223/* source is YUV420P */
224static CSC_ERRORCODE conv_sw_src_yuv420p(
225 CSC_HANDLE *handle)
226{
227 CSC_ERRORCODE ret = CSC_ErrorNone;
228
229 switch (handle->dst_format.color_format) {
230 case HAL_PIXEL_FORMAT_YCbCr_420_P: /* bypass */
231 memcpy((unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
232 (unsigned char *)handle->src_buffer.planes[CSC_Y_PLANE],
233 handle->src_format.width * handle->src_format.height);
234 memcpy((unsigned char *)handle->dst_buffer.planes[CSC_U_PLANE],
235 (unsigned char *)handle->src_buffer.planes[CSC_U_PLANE],
236 (handle->src_format.width * handle->src_format.height) >> 2);
237 memcpy((unsigned char *)handle->dst_buffer.planes[CSC_V_PLANE],
238 (unsigned char *)handle->src_buffer.planes[CSC_V_PLANE],
239 (handle->src_format.width * handle->src_format.height) >> 2);
240 ret = CSC_ErrorNone;
241 break;
242 case HAL_PIXEL_FORMAT_YCbCr_420_SP:
243 memcpy((unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
244 (unsigned char *)handle->src_buffer.planes[CSC_Y_PLANE],
245 handle->src_format.width * handle->src_format.height);
246 csc_interleave_memcpy_neon(
247 (unsigned char *)handle->dst_buffer.planes[CSC_UV_PLANE],
248 (unsigned char *)handle->src_buffer.planes[CSC_U_PLANE],
249 (unsigned char *)handle->src_buffer.planes[CSC_V_PLANE],
250 (handle->src_format.width * handle->src_format.height) >> 2);
251 ret = CSC_ErrorNone;
252 break;
253 default:
254 ret = CSC_ErrorUnsupportFormat;
255 break;
256 }
257
258 return ret;
259}
260
261/* source is YUV420SP */
262static CSC_ERRORCODE conv_sw_src_yuv420sp(
263 CSC_HANDLE *handle)
264{
265 CSC_ERRORCODE ret = CSC_ErrorNone;
266
267 switch (handle->dst_format.color_format) {
268 case HAL_PIXEL_FORMAT_YCbCr_420_P:
269 memcpy((unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
270 (unsigned char *)handle->src_buffer.planes[CSC_Y_PLANE],
271 handle->src_format.width * handle->src_format.height);
272 csc_deinterleave_memcpy(
273 (unsigned char *)handle->dst_buffer.planes[CSC_U_PLANE],
274 (unsigned char *)handle->dst_buffer.planes[CSC_V_PLANE],
275 (unsigned char *)handle->src_buffer.planes[CSC_UV_PLANE],
276 handle->src_format.width * handle->src_format.height >> 1);
277 ret = CSC_ErrorNone;
278 break;
279 case HAL_PIXEL_FORMAT_YCbCr_420_SP: /* bypass */
280 memcpy((unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
281 (unsigned char *)handle->src_buffer.planes[CSC_Y_PLANE],
282 handle->src_format.width * handle->src_format.height);
283 memcpy((unsigned char *)handle->dst_buffer.planes[CSC_UV_PLANE],
284 (unsigned char *)handle->src_buffer.planes[CSC_UV_PLANE],
285 handle->src_format.width * handle->src_format.height >> 1);
286 ret = CSC_ErrorNone;
287 break;
288 default:
289 ret = CSC_ErrorUnsupportFormat;
290 break;
291 }
292
293 return ret;
294}
295
296static CSC_ERRORCODE conv_sw(
297 CSC_HANDLE *handle)
298{
299 CSC_ERRORCODE ret = CSC_ErrorNone;
300
301 switch (handle->src_format.color_format) {
302 case HAL_PIXEL_FORMAT_YCbCr_420_SP_TILED:
303 ret = conv_sw_src_nv12t(handle);
304 break;
305 case HAL_PIXEL_FORMAT_YCbCr_420_P:
306 ret = conv_sw_src_yuv420p(handle);
307 break;
308 case HAL_PIXEL_FORMAT_YCbCr_420_SP:
309 ret = conv_sw_src_yuv420sp(handle);
310 break;
311 case HAL_PIXEL_FORMAT_ARGB888:
312 ret = conv_sw_src_argb888(handle);
313 break;
314 default:
315 ret = CSC_ErrorUnsupportFormat;
316 break;
317 }
318
319 return ret;
320}
321
322static CSC_ERRORCODE conv_hw(
323 CSC_HANDLE *handle)
324{
325 CSC_ERRORCODE ret = CSC_ErrorNone;
326
327 switch (handle->csc_hw_type) {
328#ifdef USE_FIMC
329 case CSC_HW_TYPE_FIMC:
330 {
331 void *src_addr[3];
332 void *dst_addr[3];
333 OMX_COLOR_FORMATTYPE omx_format;
334 src_addr[0] = handle->src_buffer.planes[CSC_Y_PLANE];
335 src_addr[1] = handle->src_buffer.planes[CSC_UV_PLANE];
336 dst_addr[0] = handle->dst_buffer.planes[CSC_Y_PLANE];
337 dst_addr[1] = handle->dst_buffer.planes[CSC_U_PLANE];
338 dst_addr[2] = handle->dst_buffer.planes[CSC_V_PLANE];
339 omx_format = hal_2_omx_pixel_format(handle->dst_format.color_format);
340 csc_hwconverter_convert_nv12t(
341 handle->csc_hw_handle,
342 dst_addr,
343 src_addr,
344 handle->dst_format.width,
345 handle->dst_format.height,
346 omx_format);
347 break;
348 }
349#endif
350#ifdef USE_GSCALER
351 case CSC_HW_TYPE_GSCALER:
352 exynos_gsc_convert(handle->csc_hw_handle);
353 break;
354#endif
355 default:
356 LOGE("%s:: unsupported csc_hw_type", __func__);
357 break;
358 }
359
360 return CSC_ErrorNotImplemented;
361}
362
363void *csc_init(
364 CSC_METHOD *method)
365{
366 CSC_HANDLE *csc_handle;
367 csc_handle = (CSC_HANDLE *)malloc(sizeof(CSC_HANDLE));
368 if (csc_handle == NULL)
369 return NULL;
370
371 memset(csc_handle, 0, sizeof(CSC_HANDLE));
372
373 csc_handle->csc_method = *method;
374
375 if (csc_handle->csc_method == CSC_METHOD_HW ||
376 csc_handle->csc_method == CSC_METHOD_PREFER_HW) {
377#ifdef USE_FIMC
378 csc_handle->csc_hw_type = CSC_HW_TYPE_FIMC;
379#endif
380#ifdef USE_GSCALER
381 csc_handle->csc_hw_type = CSC_HW_TYPE_GSCALER;
382#endif
383 switch (csc_handle->csc_hw_type) {
384#ifdef USE_FIMC
385 case CSC_HW_TYPE_FIMC:
386 csc_handle->csc_hw_handle = csc_hwconverter_open();
387 LOGD("%s:: CSC_HW_TYPE_FIMC", __func__);
388 break;
389#endif
390#ifdef USE_GSCALER
391 case CSC_HW_TYPE_GSCALER:
392 csc_handle->csc_hw_handle = exynos_gsc_create();
393 LOGD("%s:: CSC_HW_TYPE_GSCALER", __func__);
394 break;
395#endif
396 default:
397 LOGE("%s:: unsupported csc_hw_type, csc use sw", __func__);
398 csc_handle->csc_hw_handle == NULL;
399 break;
400 }
401 }
402
403 if (csc_handle->csc_method == CSC_METHOD_PREFER_HW) {
404 if (csc_handle->csc_hw_handle == NULL) {
405 csc_handle->csc_method = CSC_METHOD_SW;
406 *method = CSC_METHOD_SW;
407 } else {
408 csc_handle->csc_method = CSC_METHOD_HW;
409 *method = CSC_METHOD_HW;
410 }
411 }
412
413 if (csc_handle->csc_method == CSC_METHOD_HW) {
414 if (csc_handle->csc_hw_handle == NULL) {
415 LOGE("%s:: CSC_METHOD_HW can't open HW", __func__);
416 free(csc_handle);
417 csc_handle = NULL;
418 }
419 }
420
421 LOGD("%s:: CSC_METHOD=%d", __func__, csc_handle->csc_method);
422
423 return (void *)csc_handle;
424}
425
426CSC_ERRORCODE csc_deinit(
427 void *handle)
428{
429 CSC_ERRORCODE ret = CSC_ErrorNone;
430 CSC_HANDLE *csc_handle;
431
432 csc_handle = (CSC_HANDLE *)handle;
433 if (csc_handle->csc_method == CSC_METHOD_HW) {
434 switch (csc_handle->csc_hw_type) {
435#ifdef USE_FIMC
436 case CSC_HW_TYPE_FIMC:
437 csc_hwconverter_close(csc_handle->csc_hw_handle);
438 break;
439#endif
440#ifdef USE_GSCALER
441 case CSC_HW_TYPE_GSCALER:
442 exynos_gsc_destroy(csc_handle->csc_hw_handle);
443 break;
444#endif
445 default:
446 LOGE("%s:: unsupported csc_hw_type", __func__);
447 break;
448 }
449 }
450
451 if (csc_handle != NULL) {
452 free(csc_handle);
453 ret = CSC_ErrorNone;
454 }
455
456 return ret;
457}
458
459CSC_ERRORCODE csc_get_method(
460 void *handle,
461 CSC_METHOD *method)
462{
463 CSC_HANDLE *csc_handle;
464 CSC_ERRORCODE ret = CSC_ErrorNone;
465
466 if (handle == NULL)
467 return CSC_ErrorNotInit;
468
469 csc_handle = (CSC_HANDLE *)handle;
470 *method = csc_handle->csc_method;
471
472 return ret;
473}
474
475CSC_ERRORCODE csc_get_src_format(
476 void *handle,
477 unsigned int *width,
478 unsigned int *height,
479 unsigned int *crop_left,
480 unsigned int *crop_top,
481 unsigned int *crop_width,
482 unsigned int *crop_height,
483 unsigned int *color_format,
484 unsigned int *cacheable)
485{
486 CSC_HANDLE *csc_handle;
487 CSC_ERRORCODE ret = CSC_ErrorNone;
488
489 if (handle == NULL)
490 return CSC_ErrorNotInit;
491
492 csc_handle = (CSC_HANDLE *)handle;
493 *width = csc_handle->src_format.width;
494 *height = csc_handle->src_format.height;
495 *crop_left = csc_handle->src_format.crop_left;
496 *crop_top = csc_handle->src_format.crop_top;
497 *crop_width = csc_handle->src_format.crop_width;
498 *crop_height = csc_handle->src_format.crop_height;
499 *color_format = csc_handle->src_format.color_format;
500 *cacheable = csc_handle->src_format.cacheable;
501
502 return ret;
503}
504
505CSC_ERRORCODE csc_set_src_format(
506 void *handle,
507 unsigned int width,
508 unsigned int height,
509 unsigned int crop_left,
510 unsigned int crop_top,
511 unsigned int crop_width,
512 unsigned int crop_height,
513 unsigned int color_format,
514 unsigned int cacheable)
515{
516 CSC_HANDLE *csc_handle;
517 CSC_ERRORCODE ret = CSC_ErrorNone;
518
519 if (handle == NULL)
520 return CSC_ErrorNotInit;
521
522 csc_handle = (CSC_HANDLE *)handle;
523 csc_handle->src_format.width = width;
524 csc_handle->src_format.height = height;
525 csc_handle->src_format.crop_left = crop_left;
526 csc_handle->src_format.crop_top = crop_top;
527 csc_handle->src_format.crop_width = crop_width;
528 csc_handle->src_format.crop_height = crop_height;
529 csc_handle->src_format.color_format = color_format;
530 csc_handle->src_format.cacheable = cacheable;
531
532 if (csc_handle->csc_method == CSC_METHOD_HW) {
533 switch (csc_handle->csc_hw_type) {
534 case CSC_HW_TYPE_FIMC:
535 break;
536#ifdef USE_GSCALER
537 case CSC_HW_TYPE_GSCALER:
538 exynos_gsc_set_src_format(
539 csc_handle->csc_hw_handle,
540 ALIGN(csc_handle->src_format.width, GSCALER_IMG_ALIGN),
541 ALIGN(csc_handle->src_format.height, GSCALER_IMG_ALIGN),
542 csc_handle->src_format.crop_left,
543 csc_handle->src_format.crop_top,
544 ALIGN(csc_handle->src_format.crop_width, GSCALER_IMG_ALIGN),
545 ALIGN(csc_handle->src_format.crop_height, GSCALER_IMG_ALIGN),
546 HAL_PIXEL_FORMAT_2_V4L2_PIX(csc_handle->src_format.color_format),
547 csc_handle->src_format.cacheable);
548 break;
549#endif
550 default:
551 LOGE("%s:: unsupported csc_hw_type", __func__);
552 break;
553 }
554 }
555
556 return ret;
557}
558
559CSC_ERRORCODE csc_get_dst_format(
560 void *handle,
561 unsigned int *width,
562 unsigned int *height,
563 unsigned int *crop_left,
564 unsigned int *crop_top,
565 unsigned int *crop_width,
566 unsigned int *crop_height,
567 unsigned int *color_format,
568 unsigned int *cacheable)
569{
570 CSC_HANDLE *csc_handle;
571 CSC_ERRORCODE ret = CSC_ErrorNone;
572
573 if (handle == NULL)
574 return CSC_ErrorNotInit;
575
576 csc_handle = (CSC_HANDLE *)handle;
577 *width = csc_handle->dst_format.width;
578 *height = csc_handle->dst_format.height;
579 *crop_left = csc_handle->dst_format.crop_left;
580 *crop_top = csc_handle->dst_format.crop_top;
581 *crop_width = csc_handle->dst_format.crop_width;
582 *crop_height = csc_handle->dst_format.crop_height;
583 *color_format = csc_handle->dst_format.color_format;
584 *cacheable = csc_handle->dst_format.cacheable;
585
586 return ret;
587}
588
589CSC_ERRORCODE csc_set_dst_format(
590 void *handle,
591 unsigned int width,
592 unsigned int height,
593 unsigned int crop_left,
594 unsigned int crop_top,
595 unsigned int crop_width,
596 unsigned int crop_height,
597 unsigned int color_format,
598 unsigned int cacheable)
599{
600 CSC_HANDLE *csc_handle;
601 CSC_ERRORCODE ret = CSC_ErrorNone;
602
603 if (handle == NULL)
604 return CSC_ErrorNotInit;
605
606 csc_handle = (CSC_HANDLE *)handle;
607 csc_handle->dst_format.width = width;
608 csc_handle->dst_format.height = height;
609 csc_handle->dst_format.crop_left = crop_left;
610 csc_handle->dst_format.crop_top = crop_top;
611 csc_handle->dst_format.crop_width = crop_width;
612 csc_handle->dst_format.crop_height = crop_height;
613 csc_handle->dst_format.color_format = color_format;
614 csc_handle->dst_format.cacheable = cacheable;
615
616 if (csc_handle->csc_method == CSC_METHOD_HW) {
617 switch (csc_handle->csc_hw_type) {
618 case CSC_HW_TYPE_FIMC:
619 break;
620#ifdef USE_GSCALER
621 case CSC_HW_TYPE_GSCALER:
622 exynos_gsc_set_dst_format(
623 csc_handle->csc_hw_handle,
624 ALIGN(csc_handle->dst_format.width, GSCALER_IMG_ALIGN),
625 ALIGN(csc_handle->dst_format.height, GSCALER_IMG_ALIGN),
626 csc_handle->dst_format.crop_left,
627 csc_handle->dst_format.crop_top,
628 ALIGN(csc_handle->dst_format.crop_width, GSCALER_IMG_ALIGN),
629 ALIGN(csc_handle->dst_format.crop_height, GSCALER_IMG_ALIGN),
630 HAL_PIXEL_FORMAT_2_V4L2_PIX(csc_handle->dst_format.color_format),
631 csc_handle->dst_format.cacheable);
632 break;
633#endif
634 default:
635 LOGE("%s:: unsupported csc_hw_type", __func__);
636 break;
637 }
638 }
639
640 return ret;
641}
642
643CSC_ERRORCODE csc_set_src_buffer(
644 void *handle,
645 unsigned char *y,
646 unsigned char *u,
647 unsigned char *v,
648 int ion_fd)
649{
650 CSC_HANDLE *csc_handle;
651 CSC_ERRORCODE ret = CSC_ErrorNone;
652 void *addr[3] = {NULL, };
653
654 if (handle == NULL)
655 return CSC_ErrorNotInit;
656
657 csc_handle = (CSC_HANDLE *)handle;
658 csc_handle->src_buffer.planes[CSC_Y_PLANE] = y;
659 csc_handle->src_buffer.planes[CSC_U_PLANE] = u;
660 csc_handle->src_buffer.planes[CSC_V_PLANE] = v;
661
662 if (csc_handle->csc_method == CSC_METHOD_HW) {
663 addr[0] = csc_handle->src_buffer.planes[CSC_Y_PLANE];
664 addr[1] = csc_handle->src_buffer.planes[CSC_U_PLANE];
665 addr[2] = csc_handle->src_buffer.planes[CSC_V_PLANE];
666
667 switch (csc_handle->csc_hw_type) {
668 case CSC_HW_TYPE_FIMC:
669 break;
670#ifdef USE_GSCALER
671 case CSC_HW_TYPE_GSCALER:
672 exynos_gsc_set_src_addr(csc_handle->csc_hw_handle, addr);
673 break;
674#endif
675 default:
676 LOGE("%s:: unsupported csc_hw_type", __func__);
677 break;
678 }
679 }
680
681 return ret;
682}
683
684CSC_ERRORCODE csc_set_dst_buffer(
685 void *handle,
686 unsigned char *y,
687 unsigned char *u,
688 unsigned char *v,
689 int ion_fd)
690{
691 CSC_HANDLE *csc_handle;
692 CSC_ERRORCODE ret = CSC_ErrorNone;
693 void *addr[3] = {NULL, };
694
695 if (handle == NULL)
696 return CSC_ErrorNotInit;
697
698 csc_handle = (CSC_HANDLE *)handle;
699 csc_handle->dst_buffer.planes[CSC_Y_PLANE] = y;
700 csc_handle->dst_buffer.planes[CSC_U_PLANE] = u;
701 csc_handle->dst_buffer.planes[CSC_V_PLANE] = v;
702
703 if (csc_handle->csc_method == CSC_METHOD_HW) {
704 addr[0] = csc_handle->dst_buffer.planes[CSC_Y_PLANE];
705 addr[1] = csc_handle->dst_buffer.planes[CSC_U_PLANE];
706 addr[2] = csc_handle->dst_buffer.planes[CSC_V_PLANE];
707
708 switch (csc_handle->csc_hw_type) {
709 case CSC_HW_TYPE_FIMC:
710 break;
711#ifdef USE_GSCALER
712 case CSC_HW_TYPE_GSCALER:
713 exynos_gsc_set_dst_addr(csc_handle->csc_hw_handle, addr);
714 break;
715#endif
716 default:
717 LOGE("%s:: unsupported csc_hw_type", __func__);
718 break;
719 }
720 }
721
722 return ret;
723}
724
725CSC_ERRORCODE csc_convert(
726 void *handle)
727{
728 CSC_HANDLE *csc_handle = (CSC_HANDLE *)handle;
729 CSC_ERRORCODE ret = CSC_ErrorNone;
730
731 if (csc_handle == NULL)
732 return CSC_ErrorNotInit;
733
734 if (csc_handle->csc_method == CSC_METHOD_HW)
735 ret = conv_hw(csc_handle);
736 else
737 ret = conv_sw(csc_handle);
738
739 return ret;
740}