fixed svace issue
[platform/adaptation/ap_samsung/libomxil-e3250-v4l2.git] / exynos / libcsc / csc.c
1 /*
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 #ifndef TIZEN_FEATURE_E3250 /* build env */
32 #include <cutils/log.h>
33 #endif
34
35 #include <stdio.h>
36 #include <stdlib.h>
37 #include <string.h>
38 #ifndef TIZEN_FEATURE_E3250 /* build env */
39 #include <utils/Log.h>
40 #include <system/graphics.h>
41 #else
42 #include "Exynos_OSAL_Log.h"
43 #endif
44
45
46 #include "csc.h"
47 #include "exynos_format.h"
48 #include "swconverter.h"
49
50 #ifdef TIZEN_FEATURE_E3250 /* build env */
51 #define EXYNOS_OMX
52 #endif
53
54 #ifdef EXYNOS_OMX
55 #include "Exynos_OMX_Def.h"
56 #else
57 #include "SEC_OMX_Def.h"
58 #endif
59
60 #ifdef ENABLE_FIMC
61 #include "hwconverter_wrapper.h"
62 #endif
63
64 #ifdef ENABLE_GSCALER
65 #include "exynos_gscaler.h"
66 #endif
67
68 #define GSCALER_IMG_ALIGN 16
69 #define CSC_MAX_PLANES 3
70 #define ALIGN(x, a)       (((x) + (a) - 1) & ~((a) - 1))
71
72 typedef enum _CSC_PLANE {
73     CSC_Y_PLANE = 0,
74     CSC_RGB_PLANE = 0,
75     CSC_U_PLANE = 1,
76     CSC_UV_PLANE = 1,
77     CSC_V_PLANE = 2
78 } CSC_PLANE;
79
80 typedef enum _CSC_HW_TYPE {
81     CSC_HW_TYPE_FIMC = 0,
82     CSC_HW_TYPE_GSCALER
83 } CSC_HW_TYPE;
84
85 typedef struct _CSC_FORMAT {
86     unsigned int width;
87     unsigned int height;
88     unsigned int crop_left;
89     unsigned int crop_top;
90     unsigned int crop_width;
91     unsigned int crop_height;
92     unsigned int color_format;
93     unsigned int cacheable;
94     unsigned int mode_drm;
95 } CSC_FORMAT;
96
97 typedef struct _CSC_BUFFER {
98     unsigned char *planes[CSC_MAX_PLANES];
99     int ion_fd;
100 } CSC_BUFFER;
101
102 typedef struct _CSC_HW_PROPERTY {
103     int fixed_node;
104     int mode_drm;
105 } CSC_HW_PROPERTY;
106
107 typedef struct _CSC_HANDLE {
108     CSC_FORMAT      dst_format;
109     CSC_FORMAT      src_format;
110     CSC_BUFFER      dst_buffer;
111     CSC_BUFFER      src_buffer;
112     CSC_METHOD      csc_method;
113     CSC_HW_TYPE     csc_hw_type;
114     void           *csc_hw_handle;
115     CSC_HW_PROPERTY hw_property;
116 } CSC_HANDLE;
117
118 /* source is RGB888 */
119 static CSC_ERRORCODE conv_sw_src_argb888(
120     CSC_HANDLE *handle)
121 {
122     CSC_ERRORCODE ret = CSC_ErrorNone;
123
124     switch (handle->dst_format.color_format) {
125     case HAL_PIXEL_FORMAT_YCbCr_420_P:
126         csc_ARGB8888_to_YUV420P(
127             (unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
128             (unsigned char *)handle->dst_buffer.planes[CSC_U_PLANE],
129             (unsigned char *)handle->dst_buffer.planes[CSC_V_PLANE],
130             (unsigned char *)handle->src_buffer.planes[CSC_RGB_PLANE],
131             handle->src_format.width,
132             handle->src_format.height);
133         ret = CSC_ErrorNone;
134         break;
135     case HAL_PIXEL_FORMAT_YCbCr_420_SP:
136 #ifdef USE_NEON
137         csc_ARGB8888_to_YUV420SP_NEON(
138 #else
139         csc_ARGB8888_to_YUV420SP(
140 #endif
141             (unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
142             (unsigned char *)handle->dst_buffer.planes[CSC_UV_PLANE],
143             (unsigned char *)handle->src_buffer.planes[CSC_RGB_PLANE],
144             handle->src_format.width,
145             handle->src_format.height);
146         ret = CSC_ErrorNone;
147         break;
148     default:
149         ret = CSC_ErrorUnsupportFormat;
150         break;
151     }
152
153     return ret;
154 }
155
156 /* source is NV12T */
157 static CSC_ERRORCODE conv_sw_src_nv12t(
158     CSC_HANDLE *handle)
159 {
160     CSC_ERRORCODE ret = CSC_ErrorNone;
161
162     switch (handle->dst_format.color_format) {
163     case HAL_PIXEL_FORMAT_YCbCr_420_P:
164         ALOGE("dst_format HAL_PIXEL_FORMAT_YCbCr_420_P");
165 #ifdef USE_NEON
166         csc_tiled_to_linear_y_neon(
167 #else
168         csc_tiled_to_linear_y(
169 #endif
170             (unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
171             (unsigned char *)handle->src_buffer.planes[CSC_Y_PLANE],
172             handle->src_format.width,
173             handle->src_format.height);
174 #ifdef USE_NEON
175         csc_tiled_to_linear_uv_deinterleave_neon(
176 #else
177         csc_tiled_to_linear_uv_deinterleave(
178 #endif
179             (unsigned char *)handle->dst_buffer.planes[CSC_U_PLANE],
180             (unsigned char *)handle->dst_buffer.planes[CSC_V_PLANE],
181             (unsigned char *)handle->src_buffer.planes[CSC_UV_PLANE],
182             handle->src_format.width,
183             handle->src_format.height / 2);
184         ret = CSC_ErrorNone;
185         break;
186     case HAL_PIXEL_FORMAT_YCbCr_420_SP:
187         ALOGE("dst_format HAL_PIXEL_FORMAT_YCbCr_420_SP");
188 #ifdef USE_NEON
189         csc_tiled_to_linear_y_neon(
190 #else
191         csc_tiled_to_linear_y(
192 #endif
193             (unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
194             (unsigned char *)handle->src_buffer.planes[CSC_Y_PLANE],
195             handle->src_format.width,
196             handle->src_format.height);
197 #ifdef USE_NEON
198         csc_tiled_to_linear_uv_neon(
199 #else
200         csc_tiled_to_linear_uv(
201 #endif
202             (unsigned char *)handle->dst_buffer.planes[CSC_UV_PLANE],
203             (unsigned char *)handle->src_buffer.planes[CSC_UV_PLANE],
204             handle->src_format.width,
205             handle->src_format.height / 2);
206         ret = CSC_ErrorNone;
207 #ifdef OUTPUT_FILE_DUMP
208         {
209             FILE *pf;
210             char filename[100];
211             static int tmp_cnt=0;
212             int w = handle->dst_buffer.width;
213             int h = handle->dst_buffer.height;
214
215             memset(filename, 0x00, sizeof(filename));
216             sprintf(filename, "/tmp/dec_dump_%d_%d_%d.yuv", w, h, ++tmp_cnt);
217
218             pf = fopen(filename, "wb");
219             if (pf == NULL) {
220                 ALOGE("[file dump] filepoint NULL!");
221             } else {
222                 ALOGE("[file dump] fwrite[%d]", tmp_cnt);
223                 fwrite(handle->dst_buffer.planes[CSC_Y_PLANE], sizeof(char), w * h, pf);
224                 fwrite(handle->dst_buffer.planes[CSC_UV_PLANE], sizeof(char), w * h / 2, pf);
225             }
226             fclose(pf);
227         }
228 #endif
229         break;
230     default:
231         ALOGE("dst_format CSC_ErrorUnsupportFormat");
232         ret = CSC_ErrorUnsupportFormat;
233         break;
234     }
235
236     return ret;
237 }
238
239 void csc_interleave_memcpy_neon(
240     unsigned char *dest,
241     unsigned char *src1,
242     unsigned char *src2,
243     unsigned int src_size);
244
245 /* source is YUV420P */
246 static CSC_ERRORCODE conv_sw_src_yuv420p(
247     CSC_HANDLE *handle)
248 {
249     CSC_ERRORCODE ret = CSC_ErrorNone;
250
251     switch (handle->dst_format.color_format) {
252     case HAL_PIXEL_FORMAT_YCbCr_420_P:  /* bypass */
253         memcpy((unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
254                (unsigned char *)handle->src_buffer.planes[CSC_Y_PLANE],
255                handle->src_format.width * handle->src_format.height);
256         memcpy((unsigned char *)handle->dst_buffer.planes[CSC_U_PLANE],
257                (unsigned char *)handle->src_buffer.planes[CSC_U_PLANE],
258                (handle->src_format.width * handle->src_format.height) >> 2);
259         memcpy((unsigned char *)handle->dst_buffer.planes[CSC_V_PLANE],
260                (unsigned char *)handle->src_buffer.planes[CSC_V_PLANE],
261                (handle->src_format.width * handle->src_format.height) >> 2);
262         ret = CSC_ErrorNone;
263         break;
264     case HAL_PIXEL_FORMAT_YCbCr_420_SP:
265         memcpy((unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
266                (unsigned char *)handle->src_buffer.planes[CSC_Y_PLANE],
267                handle->src_format.width * handle->src_format.height);
268 #ifdef USE_NEON
269         csc_interleave_memcpy_neon(
270 #else
271         csc_interleave_memcpy(
272 #endif
273             (unsigned char *)handle->dst_buffer.planes[CSC_UV_PLANE],
274             (unsigned char *)handle->src_buffer.planes[CSC_U_PLANE],
275             (unsigned char *)handle->src_buffer.planes[CSC_V_PLANE],
276             (handle->src_format.width * handle->src_format.height) >> 2);
277         ret = CSC_ErrorNone;
278         break;
279     default:
280         ret = CSC_ErrorUnsupportFormat;
281         break;
282     }
283
284     return ret;
285 }
286
287 /* source is YUV420SP */
288 static CSC_ERRORCODE conv_sw_src_yuv420sp(
289     CSC_HANDLE *handle)
290 {
291     CSC_ERRORCODE ret = CSC_ErrorNone;
292
293     switch (handle->dst_format.color_format) {
294     case HAL_PIXEL_FORMAT_YCbCr_420_P:
295         memcpy((unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
296                (unsigned char *)handle->src_buffer.planes[CSC_Y_PLANE],
297                handle->src_format.width * handle->src_format.height);
298         csc_deinterleave_memcpy(
299             (unsigned char *)handle->dst_buffer.planes[CSC_U_PLANE],
300             (unsigned char *)handle->dst_buffer.planes[CSC_V_PLANE],
301             (unsigned char *)handle->src_buffer.planes[CSC_UV_PLANE],
302             handle->src_format.width * handle->src_format.height >> 1);
303         ret = CSC_ErrorNone;
304         break;
305     case HAL_PIXEL_FORMAT_YCbCr_420_SP: /* bypass */
306         memcpy((unsigned char *)handle->dst_buffer.planes[CSC_Y_PLANE],
307                (unsigned char *)handle->src_buffer.planes[CSC_Y_PLANE],
308                handle->src_format.width * handle->src_format.height);
309         memcpy((unsigned char *)handle->dst_buffer.planes[CSC_UV_PLANE],
310                (unsigned char *)handle->src_buffer.planes[CSC_UV_PLANE],
311                handle->src_format.width * handle->src_format.height >> 1);
312         ret = CSC_ErrorNone;
313         break;
314     default:
315         ret = CSC_ErrorUnsupportFormat;
316         break;
317     }
318
319     return ret;
320 }
321
322 static CSC_ERRORCODE conv_sw(
323     CSC_HANDLE *handle)
324 {
325     CSC_ERRORCODE ret = CSC_ErrorNone;
326
327     ALOGE("%s:: handle->src_format.color_format = %d", __func__, handle->src_format.color_format);
328     switch (handle->src_format.color_format) {
329     case HAL_PIXEL_FORMAT_YCbCr_420_SP_TILED:
330     ALOGE("src_format HAL_PIXEL_FORMAT_YCbCr_420_SP_TILED");
331         ret = conv_sw_src_nv12t(handle);
332         break;
333     case HAL_PIXEL_FORMAT_YCbCr_420_P:
334     ALOGE("src_format HAL_PIXEL_FORMAT_YCbCr_420_P");
335         ret = conv_sw_src_yuv420p(handle);
336         break;
337     case HAL_PIXEL_FORMAT_YCbCr_420_SP:
338     ALOGE("src_format HAL_PIXEL_FORMAT_YCbCr_420_SP");
339         ret = conv_sw_src_yuv420sp(handle);
340         break;
341     case HAL_PIXEL_FORMAT_ARGB888:
342     ALOGE("src_format HAL_PIXEL_FORMAT_ARGB888");
343         ret = conv_sw_src_argb888(handle);
344         break;
345     default:
346         ret = CSC_ErrorUnsupportFormat;
347         break;
348     }
349
350     return ret;
351 }
352
353 static CSC_ERRORCODE conv_hw(
354     CSC_HANDLE *handle)
355 {
356     CSC_ERRORCODE ret = CSC_ErrorNone;
357     switch (handle->csc_hw_type) {
358 #ifdef ENABLE_FIMC
359     case CSC_HW_TYPE_FIMC:
360     {
361         void *src_addr[3];
362         void *dst_addr[3];
363         OMX_COLOR_FORMATTYPE src_omx_format;
364         OMX_COLOR_FORMATTYPE dst_omx_format;
365         src_addr[0] = handle->src_buffer.planes[CSC_Y_PLANE];
366         src_addr[1] = handle->src_buffer.planes[CSC_UV_PLANE];
367         dst_addr[0] = handle->dst_buffer.planes[CSC_Y_PLANE];
368         dst_addr[1] = handle->dst_buffer.planes[CSC_U_PLANE];
369         dst_addr[2] = handle->dst_buffer.planes[CSC_V_PLANE];
370         src_omx_format = hal_2_omx_pixel_format(handle->src_format.color_format);
371         dst_omx_format = hal_2_omx_pixel_format(handle->dst_format.color_format);
372         csc_hwconverter_convert_nv12t(
373             handle->csc_hw_handle,
374             dst_addr,
375             src_addr,
376             handle->dst_format.width,
377             handle->dst_format.height,
378             dst_omx_format,
379             src_omx_format);
380         break;
381     }
382 #endif
383 #ifdef ENABLE_GSCALER
384     case CSC_HW_TYPE_GSCALER:
385         if (exynos_gsc_convert(handle->csc_hw_handle) != 0) {
386             ALOGE("%s:: exynos_gsc_convert() fail", __func__);
387             ret = CSC_Error;
388         }
389         break;
390 #endif
391     default:
392         ALOGE("%s:: unsupported csc_hw_type(%d)", __func__, handle->csc_hw_type);
393         ret = CSC_ErrorNotImplemented;
394         break;
395     }
396
397     return ret;
398 }
399
400 static CSC_ERRORCODE csc_init_hw(
401     void *handle)
402 {
403     CSC_HANDLE *csc_handle;
404     CSC_ERRORCODE ret = CSC_ErrorNone;
405
406     csc_handle = (CSC_HANDLE *)handle;
407     if (csc_handle->csc_method == CSC_METHOD_HW) {
408 #ifdef ENABLE_FIMC
409         csc_handle->csc_hw_type = CSC_HW_TYPE_FIMC;
410 #endif
411 #ifdef ENABLE_GSCALER
412         csc_handle->csc_hw_type = CSC_HW_TYPE_GSCALER;
413 #endif
414         switch (csc_handle->csc_hw_type) {
415 #ifdef ENABLE_FIMC
416         case CSC_HW_TYPE_FIMC:
417             csc_handle->csc_hw_handle = csc_hwconverter_open();
418             ALOGV("%s:: CSC_HW_TYPE_FIMC", __func__);
419             break;
420 #endif
421 #ifdef ENABLE_GSCALER
422         case CSC_HW_TYPE_GSCALER:
423             if (csc_handle->hw_property.fixed_node >= 0)
424                 csc_handle->csc_hw_handle = exynos_gsc_create_exclusive(csc_handle->hw_property.fixed_node, GSC_M2M_MODE, 0);
425             else
426             csc_handle->csc_hw_handle = exynos_gsc_create();
427             ALOGV("%s:: CSC_HW_TYPE_GSCALER", __func__);
428             break;
429 #endif
430         default:
431             ALOGE("%s:: unsupported csc_hw_type, csc use sw", __func__);
432             csc_handle->csc_hw_handle = NULL;
433             break;
434         }
435     }
436
437     if (csc_handle->csc_method == CSC_METHOD_HW) {
438         if (csc_handle->csc_hw_handle == NULL) {
439             ALOGE("%s:: CSC_METHOD_HW can't open HW", __func__);
440             free(csc_handle);
441             csc_handle = NULL;
442             return CSC_ErrorNotInit;
443         }
444     }
445
446     ALOGV("%s:: CSC_METHOD=%d", __func__, csc_handle->csc_method);
447
448     return ret;
449 }
450
451 static CSC_ERRORCODE csc_set_format(
452     void *handle)
453 {
454     CSC_HANDLE *csc_handle;
455     CSC_ERRORCODE ret = CSC_ErrorNone;
456
457     if (handle == NULL)
458         return CSC_ErrorNotInit;
459
460     csc_handle = (CSC_HANDLE *)handle;
461     if (csc_handle->csc_method == CSC_METHOD_HW) {
462         switch (csc_handle->csc_hw_type) {
463         case CSC_HW_TYPE_FIMC:
464             break;
465 #ifdef ENABLE_GSCALER
466         case CSC_HW_TYPE_GSCALER:
467             exynos_gsc_set_src_format(
468                 csc_handle->csc_hw_handle,
469                 ALIGN(csc_handle->src_format.width, GSCALER_IMG_ALIGN),
470                 ALIGN(csc_handle->src_format.height, GSCALER_IMG_ALIGN),
471                 csc_handle->src_format.crop_left,
472                 csc_handle->src_format.crop_top,
473                 csc_handle->src_format.crop_width,
474                 csc_handle->src_format.crop_height,
475                 HAL_PIXEL_FORMAT_2_V4L2_PIX(csc_handle->src_format.color_format),
476                 csc_handle->src_format.cacheable,
477                 csc_handle->hw_property.mode_drm);
478
479             exynos_gsc_set_dst_format(
480                 csc_handle->csc_hw_handle,
481                 ALIGN(csc_handle->dst_format.width, GSCALER_IMG_ALIGN),
482                 ALIGN(csc_handle->dst_format.height, GSCALER_IMG_ALIGN),
483                 csc_handle->dst_format.crop_left,
484                 csc_handle->dst_format.crop_top,
485                 csc_handle->dst_format.crop_width,
486                 csc_handle->dst_format.crop_height,
487                 HAL_PIXEL_FORMAT_2_V4L2_PIX(csc_handle->dst_format.color_format),
488                 csc_handle->dst_format.cacheable,
489                 csc_handle->hw_property.mode_drm);
490             break;
491 #endif
492         default:
493             ALOGE("%s:: unsupported csc_hw_type", __func__);
494             break;
495         }
496     }
497
498     return ret;
499 }
500
501 static CSC_ERRORCODE csc_set_buffer(
502     void *handle)
503 {
504     CSC_HANDLE *csc_handle;
505     CSC_ERRORCODE ret = CSC_ErrorNone;
506 #ifdef ENABLE_GSCALER
507     void *src_addr[3] = {NULL, };
508     void *dst_addr[3] = {NULL, };
509 #endif
510
511     if (handle == NULL)
512         return CSC_ErrorNotInit;
513
514     csc_handle = (CSC_HANDLE *)handle;
515     if (csc_handle->csc_method == CSC_METHOD_HW) {
516 #ifdef ENABLE_GSCALER
517         src_addr[0] = csc_handle->src_buffer.planes[CSC_Y_PLANE];
518         src_addr[1] = csc_handle->src_buffer.planes[CSC_U_PLANE];
519         src_addr[2] = csc_handle->src_buffer.planes[CSC_V_PLANE];
520         dst_addr[0] = csc_handle->dst_buffer.planes[CSC_Y_PLANE];
521         dst_addr[1] = csc_handle->dst_buffer.planes[CSC_U_PLANE];
522         dst_addr[2] = csc_handle->dst_buffer.planes[CSC_V_PLANE];
523 #endif
524
525         switch (csc_handle->csc_hw_type) {
526         case CSC_HW_TYPE_FIMC:
527             break;
528 #ifdef ENABLE_GSCALER
529         case CSC_HW_TYPE_GSCALER:
530             exynos_gsc_set_src_addr(csc_handle->csc_hw_handle, src_addr);
531             exynos_gsc_set_dst_addr(csc_handle->csc_hw_handle, dst_addr);
532             break;
533 #endif
534         default:
535             ALOGE("%s:: unsupported csc_hw_type", __func__);
536             break;
537         }
538     }
539
540     return ret;
541 }
542
543 void *csc_init(
544     CSC_METHOD method)
545 {
546     CSC_HANDLE *csc_handle;
547     csc_handle = (CSC_HANDLE *)malloc(sizeof(CSC_HANDLE));
548     if (csc_handle == NULL)
549         return NULL;
550
551     memset(csc_handle, 0, sizeof(CSC_HANDLE));
552     csc_handle->hw_property.fixed_node = -1;
553     csc_handle->hw_property.mode_drm = 0;
554     csc_handle->csc_method = method;
555
556     return (void *)csc_handle;
557 }
558
559 CSC_ERRORCODE csc_deinit(
560     void *handle)
561 {
562     CSC_ERRORCODE ret = CSC_ErrorNone;
563     CSC_HANDLE *csc_handle;
564
565     csc_handle = (CSC_HANDLE *)handle;
566     if (csc_handle->csc_method == CSC_METHOD_HW) {
567         switch (csc_handle->csc_hw_type) {
568 #ifdef ENABLE_FIMC
569         case CSC_HW_TYPE_FIMC:
570             csc_hwconverter_close(csc_handle->csc_hw_handle);
571             break;
572 #endif
573 #ifdef ENABLE_GSCALER
574         case CSC_HW_TYPE_GSCALER:
575             exynos_gsc_destroy(csc_handle->csc_hw_handle);
576             break;
577 #endif
578         default:
579             ALOGE("%s:: unsupported csc_hw_type", __func__);
580             break;
581         }
582     }
583
584     if (csc_handle != NULL) {
585         free(csc_handle);
586         ret = CSC_ErrorNone;
587     }
588
589     return ret;
590 }
591
592 CSC_ERRORCODE csc_get_method(
593     void           *handle,
594     CSC_METHOD     *method)
595 {
596     CSC_HANDLE *csc_handle;
597     CSC_ERRORCODE ret = CSC_ErrorNone;
598
599     if (handle == NULL)
600         return CSC_ErrorNotInit;
601
602     csc_handle = (CSC_HANDLE *)handle;
603     *method = csc_handle->csc_method;
604
605     return ret;
606 }
607
608 CSC_ERRORCODE csc_set_hw_property(
609     void                *handle,
610     CSC_HW_PROPERTY_TYPE property,
611     int                  value)
612 {
613     CSC_HANDLE *csc_handle;
614     CSC_ERRORCODE ret = CSC_ErrorNone;
615
616     if (handle == NULL)
617         return CSC_ErrorNotInit;
618
619     csc_handle = (CSC_HANDLE *)handle;
620     switch (property) {
621     case CSC_HW_PROPERTY_FIXED_NODE:
622         csc_handle->hw_property.fixed_node = value;
623         break;
624     case CSC_HW_PROPERTY_MODE_DRM:
625         csc_handle->hw_property.mode_drm = value;
626         break;
627     default:
628         ALOGE("%s:: not supported hw property", __func__);
629         ret = CSC_ErrorUnsupportFormat;
630     }
631
632     return ret;
633 }
634
635 CSC_ERRORCODE csc_get_src_format(
636     void           *handle,
637     unsigned int   *width,
638     unsigned int   *height,
639     unsigned int   *crop_left,
640     unsigned int   *crop_top,
641     unsigned int   *crop_width,
642     unsigned int   *crop_height,
643     unsigned int   *color_format,
644     unsigned int   *cacheable)
645 {
646     CSC_HANDLE *csc_handle;
647     CSC_ERRORCODE ret = CSC_ErrorNone;
648
649     if (handle == NULL)
650         return CSC_ErrorNotInit;
651
652     csc_handle = (CSC_HANDLE *)handle;
653     *width = csc_handle->src_format.width;
654     *height = csc_handle->src_format.height;
655     *crop_left = csc_handle->src_format.crop_left;
656     *crop_top = csc_handle->src_format.crop_top;
657     *crop_width = csc_handle->src_format.crop_width;
658     *crop_height = csc_handle->src_format.crop_height;
659     *color_format = csc_handle->src_format.color_format;
660     *cacheable = csc_handle->src_format.cacheable;
661
662     return ret;
663 }
664
665 CSC_ERRORCODE csc_set_src_format(
666     void           *handle,
667     unsigned int    width,
668     unsigned int    height,
669     unsigned int    crop_left,
670     unsigned int    crop_top,
671     unsigned int    crop_width,
672     unsigned int    crop_height,
673     unsigned int    color_format,
674     unsigned int    cacheable)
675 {
676     CSC_HANDLE *csc_handle;
677     CSC_ERRORCODE ret = CSC_ErrorNone;
678
679     if (handle == NULL)
680         return CSC_ErrorNotInit;
681
682     csc_handle = (CSC_HANDLE *)handle;
683     csc_handle->src_format.width = width;
684     csc_handle->src_format.height = height;
685     csc_handle->src_format.crop_left = crop_left;
686     csc_handle->src_format.crop_top = crop_top;
687     csc_handle->src_format.crop_width = crop_width;
688     csc_handle->src_format.crop_height = crop_height;
689     csc_handle->src_format.color_format = color_format;
690     csc_handle->src_format.cacheable = cacheable;
691
692     return ret;
693 }
694
695 CSC_ERRORCODE csc_get_dst_format(
696     void           *handle,
697     unsigned int   *width,
698     unsigned int   *height,
699     unsigned int   *crop_left,
700     unsigned int   *crop_top,
701     unsigned int   *crop_width,
702     unsigned int   *crop_height,
703     unsigned int   *color_format,
704     unsigned int   *cacheable)
705 {
706     CSC_HANDLE *csc_handle;
707     CSC_ERRORCODE ret = CSC_ErrorNone;
708
709     if (handle == NULL)
710         return CSC_ErrorNotInit;
711
712     csc_handle = (CSC_HANDLE *)handle;
713     *width = csc_handle->dst_format.width;
714     *height = csc_handle->dst_format.height;
715     *crop_left = csc_handle->dst_format.crop_left;
716     *crop_top = csc_handle->dst_format.crop_top;
717     *crop_width = csc_handle->dst_format.crop_width;
718     *crop_height = csc_handle->dst_format.crop_height;
719     *color_format = csc_handle->dst_format.color_format;
720     *cacheable = csc_handle->dst_format.cacheable;
721
722     return ret;
723 }
724
725 CSC_ERRORCODE csc_set_dst_format(
726     void           *handle,
727     unsigned int    width,
728     unsigned int    height,
729     unsigned int    crop_left,
730     unsigned int    crop_top,
731     unsigned int    crop_width,
732     unsigned int    crop_height,
733     unsigned int    color_format,
734     unsigned int    cacheable)
735 {
736     CSC_HANDLE *csc_handle;
737     CSC_ERRORCODE ret = CSC_ErrorNone;
738
739     if (handle == NULL)
740         return CSC_ErrorNotInit;
741
742     csc_handle = (CSC_HANDLE *)handle;
743     csc_handle->dst_format.width = width;
744     csc_handle->dst_format.height = height;
745     csc_handle->dst_format.crop_left = crop_left;
746     csc_handle->dst_format.crop_top = crop_top;
747     csc_handle->dst_format.crop_width = crop_width;
748     csc_handle->dst_format.crop_height = crop_height;
749     csc_handle->dst_format.color_format = color_format;
750     csc_handle->dst_format.cacheable = cacheable;
751
752     return ret;
753 }
754
755 CSC_ERRORCODE csc_set_src_buffer(
756     void           *handle,
757     unsigned char  *y,
758     unsigned char  *u,
759     unsigned char  *v,
760     int             ion_fd)
761 {
762     CSC_HANDLE *csc_handle;
763     CSC_ERRORCODE ret = CSC_ErrorNone;
764
765     if (handle == NULL)
766         return CSC_ErrorNotInit;
767
768     csc_handle = (CSC_HANDLE *)handle;
769     csc_handle->src_buffer.planes[CSC_Y_PLANE] = y;
770     csc_handle->src_buffer.planes[CSC_U_PLANE] = u;
771     csc_handle->src_buffer.planes[CSC_V_PLANE] = v;
772
773     return ret;
774 }
775
776 CSC_ERRORCODE csc_set_dst_buffer(
777     void           *handle,
778     unsigned char  *y,
779     unsigned char  *u,
780     unsigned char  *v,
781     int             ion_fd)
782 {
783     CSC_HANDLE *csc_handle;
784     CSC_ERRORCODE ret = CSC_ErrorNone;
785
786     if (handle == NULL)
787         return CSC_ErrorNotInit;
788
789     csc_handle = (CSC_HANDLE *)handle;
790     csc_handle->dst_buffer.planes[CSC_Y_PLANE] = y;
791     csc_handle->dst_buffer.planes[CSC_U_PLANE] = u;
792     csc_handle->dst_buffer.planes[CSC_V_PLANE] = v;
793
794     return ret;
795 }
796
797 CSC_ERRORCODE csc_convert(
798     void *handle)
799 {
800     CSC_HANDLE *csc_handle = (CSC_HANDLE *)handle;
801     CSC_ERRORCODE ret = CSC_ErrorNone;
802
803     if (csc_handle == NULL)
804         return CSC_ErrorNotInit;
805
806     if ((csc_handle->csc_method == CSC_METHOD_HW) &&
807         (csc_handle->csc_hw_handle == NULL))
808         ret = csc_init_hw(handle);
809
810     if (ret != CSC_ErrorNone)
811         return ret;
812
813     csc_set_format(csc_handle);
814     csc_set_buffer(csc_handle);
815
816     if (csc_handle->csc_method == CSC_METHOD_HW) {
817     ALOGE("conv_hw");
818         ret = conv_hw(csc_handle);
819         }
820     else {
821     ALOGE("conv_sw");
822         ret = conv_sw(csc_handle);
823     ALOGE("after conv_sw");
824         }
825
826     return ret;
827 }