video: rockchip: iep: add drm support
[firefly-linux-kernel-4.4.55.git] / drivers / video / rockchip / iep / hw_iep_reg.c
1 /* 
2  * Copyright (C) 2013 ROCKCHIP, Inc.
3  *
4  * This software is licensed under the terms of the GNU General Public
5  * License version 2, as published by the Free Software Foundation, and
6  * may be copied, distributed, and modified under those terms.
7  *
8  * This program is distributed in the hope that it will be useful,
9  * but WITHOUT ANY WARRANTY; without even the implied warranty of
10  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11  * GNU General Public License for more details.
12  *
13  */
14
15 #include <linux/delay.h>
16 #include <linux/slab.h>
17 #include "iep_iommu_ops.h"
18 #include "hw_iep_reg.h"
19 #include "iep.h"
20 #include "hw_iep_config_addr.h"
21
22 extern iep_service_info iep_service;
23 static void iep_config_src_size(struct IEP_MSG *iep_msg)
24 {
25         IEP_REGB_SRC_IMG_WIDTH(iep_msg->base, iep_msg->src.act_w - 1);
26         IEP_REGB_SRC_IMG_HEIGHT(iep_msg->base, iep_msg->src.act_h - 1);
27 #ifdef IEP_PRINT_INFO
28         IEP_DBG(" //==source image size config===================//\n\n");
29         IEP_DBG("sw_src_img_height          = %d;//source image height \n",
30                 iep_msg->src.act_h - 1);
31         IEP_DBG("sw_src_img_width           = %d;//source image width \n\n",
32                 iep_msg->src.act_w - 1);
33 #endif
34 }
35
36 static void iep_config_dst_size(struct IEP_MSG *iep_msg)
37 {
38         IEP_REGB_DST_IMG_WIDTH(iep_msg->base, iep_msg->dst.act_w - 1);
39         IEP_REGB_DST_IMG_HEIGHT(iep_msg->base, iep_msg->dst.act_h - 1);
40 #ifdef IEP_PRINT_INFO
41         IEP_DBG(" //==destination image size config===================//\n\n");
42         IEP_DBG("sw_dst_img_height          = %d;//source image height \n",
43                 iep_msg->dst.act_h - 1);
44         IEP_DBG("sw_dst_img_width           = %d;//source image width \n",
45                 iep_msg->dst.act_w - 1);
46 #endif
47 }
48
49 static void iep_config_dst_width_tile(struct IEP_MSG *iep_msg)
50 {
51         /*IEP_REGB_DST_IMG_WIDTH_TILE0();
52         IEP_REGB_DST_IMG_WIDTH_TILE1();
53         IEP_REGB_DST_IMG_WIDTH_TILE2();
54         IEP_REGB_DST_IMG_WIDTH_TILE3();*/
55 #ifdef IEP_PRINT_INFO
56         IEP_DBG("sw_dst_width_tile0         = 0;\n");
57         IEP_DBG("sw_dst_width_tile1         = 0;\n");
58         IEP_DBG("sw_dst_width_tile2         = 0;\n");
59         IEP_DBG("sw_dst_width_tile3         = 0;\n\n");
60 #endif
61 }
62
63 static void iep_config_dst_fmt(struct IEP_MSG *iep_msg)
64 {
65         unsigned int dst_fmt = 0;
66         unsigned int dst_rgb_swap = 0;
67         unsigned int dst_yuv_swap = 0;
68         switch (iep_msg->dst.format) {
69         case IEP_FORMAT_ARGB_8888 :
70                 IEP_REGB_DST_FMT(iep_msg->base, 0);
71                 IEP_REGB_DST_RGB_SWAP(iep_msg->base, 0);
72                 dst_fmt = 0;
73                 dst_rgb_swap = 0;
74                 dst_yuv_swap = 0;
75                 break;
76         case IEP_FORMAT_ABGR_8888 :
77                 IEP_REGB_DST_FMT(iep_msg->base, 0);
78                 IEP_REGB_DST_RGB_SWAP(iep_msg->base, 1);
79                 dst_fmt = 0;
80                 dst_rgb_swap = 1;
81                 dst_yuv_swap = 0;
82                 break;
83         case IEP_FORMAT_RGBA_8888 :
84                 IEP_REGB_DST_FMT(iep_msg->base, 0);
85                 IEP_REGB_DST_RGB_SWAP(iep_msg->base, 2);
86                 dst_fmt = 0;
87                 dst_rgb_swap = 2;
88                 dst_yuv_swap = 0;
89                 break;
90         case IEP_FORMAT_BGRA_8888 :
91                 IEP_REGB_DST_FMT(iep_msg->base, 0);
92                 IEP_REGB_DST_RGB_SWAP(iep_msg->base, 3);
93                 dst_fmt = 0;
94                 dst_rgb_swap = 3;
95                 dst_yuv_swap = 0;
96                 break;
97         case IEP_FORMAT_RGB_565 :
98                 IEP_REGB_DST_FMT(iep_msg->base, 1);
99                 IEP_REGB_DST_RGB_SWAP(iep_msg->base, 0);
100                 dst_fmt = 1;
101                 dst_rgb_swap = 0;
102                 dst_yuv_swap = 0;
103                 break;
104         case IEP_FORMAT_BGR_565 :
105                 IEP_REGB_DST_FMT(iep_msg->base, 1);
106                 IEP_REGB_DST_RGB_SWAP(iep_msg->base, 1);
107                 dst_fmt = 1;
108                 dst_rgb_swap = 1;
109                 dst_yuv_swap = 0;
110                 break;
111         case IEP_FORMAT_YCbCr_422_SP :
112                 IEP_REGB_DST_FMT(iep_msg->base, 2);
113                 IEP_REGB_DST_YUV_SWAP(iep_msg->base, 0);
114                 dst_fmt = 2;
115                 dst_yuv_swap = 0;
116                 break;
117         case IEP_FORMAT_YCbCr_422_P :
118                 IEP_REGB_DST_FMT(iep_msg->base, 2);
119                 IEP_REGB_DST_YUV_SWAP(iep_msg->base, 2);
120                 dst_fmt = 2;
121                 dst_yuv_swap = 2;
122                 break;
123         case IEP_FORMAT_YCbCr_420_SP :
124                 IEP_REGB_DST_FMT(iep_msg->base, 3);
125                 IEP_REGB_DST_YUV_SWAP(iep_msg->base, 0);
126                 dst_fmt = 3;
127                 dst_yuv_swap = 0;
128                 break;
129         case IEP_FORMAT_YCbCr_420_P :
130                 IEP_REGB_DST_FMT(iep_msg->base, 3);
131                 IEP_REGB_DST_YUV_SWAP(iep_msg->base, 2);
132                 dst_fmt = 3;
133                 dst_yuv_swap = 2;
134                 break;
135         case IEP_FORMAT_YCrCb_422_SP :
136                 IEP_REGB_DST_FMT(iep_msg->base, 2);
137                 IEP_REGB_DST_YUV_SWAP(iep_msg->base, 1);
138                 dst_fmt = 2;
139                 dst_yuv_swap = 1;
140                 break;
141         case IEP_FORMAT_YCrCb_422_P :
142                 IEP_REGB_DST_FMT(iep_msg->base, 2);
143                 IEP_REGB_DST_YUV_SWAP(iep_msg->base, 2);
144                 dst_fmt = 2;
145                 dst_yuv_swap = 2;
146                 break;
147         case IEP_FORMAT_YCrCb_420_SP :
148                 IEP_REGB_DST_FMT(iep_msg->base, 3);
149                 IEP_REGB_DST_YUV_SWAP(iep_msg->base, 1);
150                 dst_fmt = 3;
151                 dst_yuv_swap = 1;
152                 break;
153         case IEP_FORMAT_YCrCb_420_P :
154                 IEP_REGB_DST_FMT(iep_msg->base, 3);
155                 IEP_REGB_DST_YUV_SWAP(iep_msg->base, 2);
156                 dst_fmt = 3;
157                 dst_yuv_swap = 2;
158                 break;
159         default:
160                 break;
161         }
162 #ifdef IEP_PRINT_INFO
163         IEP_DBG(" //==destination data format config============//\n\n");
164         IEP_DBG("sw_dst_yuv_swap            = %d;//0:sp uv; 1:sp vu; 2:p ;"
165                 " 3:p;\n",
166                 dst_yuv_swap);
167         IEP_DBG("sw_dst_rgb_swap            = %d;//if ARGB 0:argb; "
168                 "1,abgr; 2:rgba; 3:bgra; if rgb565: 0,2:rgb; 1,3:bgr;\n",
169                 dst_rgb_swap);
170         IEP_DBG("sw_dst_fmt                 = %d;//0:argb; 1:rgb565; 2:yuv422;"
171                 " 3:yuv420;\n\n", dst_fmt);
172 #endif
173 }
174
175 static void iep_config_src_fmt(struct IEP_MSG *iep_msg)
176 {
177         unsigned int src_fmt = 0;
178         unsigned int src_rgb_swap = 0;
179         unsigned int src_yuv_swap = 0;
180         switch (iep_msg->src.format) {
181         case IEP_FORMAT_ARGB_8888 :
182                 IEP_REGB_SRC_FMT(iep_msg->base, 0);
183                 IEP_REGB_SRC_RGB_SWAP(iep_msg->base, 0);
184                 src_fmt = 0;
185                 src_rgb_swap = 0;
186                 break;
187         case IEP_FORMAT_ABGR_8888 :
188                 IEP_REGB_SRC_FMT(iep_msg->base, 0);
189                 IEP_REGB_SRC_RGB_SWAP(iep_msg->base, 1);
190                 src_fmt = 0;
191                 src_rgb_swap = 1;
192                 break;
193         case IEP_FORMAT_RGBA_8888 :
194                 IEP_REGB_SRC_FMT(iep_msg->base, 0);
195                 IEP_REGB_SRC_RGB_SWAP(iep_msg->base, 2);
196                 src_fmt = 0;
197                 src_rgb_swap = 2;
198                 break;
199         case IEP_FORMAT_BGRA_8888 :
200                 IEP_REGB_SRC_FMT(iep_msg->base, 0);
201                 IEP_REGB_SRC_RGB_SWAP(iep_msg->base, 3);
202                 src_fmt = 0;
203                 src_rgb_swap = 3;
204                 break;
205         case IEP_FORMAT_RGB_565 :
206                 IEP_REGB_SRC_FMT(iep_msg->base, 1);
207                 IEP_REGB_SRC_RGB_SWAP(iep_msg->base, 0);
208                 src_fmt = 1;
209                 src_rgb_swap = 0;
210                 break;
211         case IEP_FORMAT_BGR_565 :
212                 IEP_REGB_SRC_FMT(iep_msg->base, 1);
213                 IEP_REGB_SRC_RGB_SWAP(iep_msg->base, 1);
214                 src_fmt = 1;
215                 src_rgb_swap = 1;
216                 break;
217         case IEP_FORMAT_YCbCr_422_SP :
218                 IEP_REGB_SRC_FMT(iep_msg->base, 2);
219                 IEP_REGB_SRC_YUV_SWAP(iep_msg->base, 0);
220                 src_fmt = 2;
221                 src_yuv_swap = 0;
222                 break;
223         case IEP_FORMAT_YCbCr_422_P :
224                 IEP_REGB_SRC_FMT(iep_msg->base, 2);
225                 IEP_REGB_SRC_YUV_SWAP(iep_msg->base, 2);
226                 src_fmt = 2;
227                 src_yuv_swap = 2;
228                 break;
229         case IEP_FORMAT_YCbCr_420_SP :
230                 IEP_REGB_SRC_FMT(iep_msg->base, 3);
231                 IEP_REGB_SRC_YUV_SWAP(iep_msg->base, 0);
232                 src_fmt = 3;
233                 src_yuv_swap = 0;
234                 break;
235         case IEP_FORMAT_YCbCr_420_P :
236                 IEP_REGB_SRC_FMT(iep_msg->base, 3);
237                 IEP_REGB_SRC_YUV_SWAP(iep_msg->base, 2);
238                 src_fmt = 3;
239                 src_yuv_swap = 2;
240                 break;
241         case IEP_FORMAT_YCrCb_422_SP :
242                 IEP_REGB_SRC_FMT(iep_msg->base, 2);
243                 IEP_REGB_SRC_YUV_SWAP(iep_msg->base, 1);
244                 src_fmt = 2;
245                 src_yuv_swap = 1;
246                 break;
247         case IEP_FORMAT_YCrCb_422_P :
248                 IEP_REGB_SRC_FMT(iep_msg->base, 2);
249                 IEP_REGB_SRC_YUV_SWAP(iep_msg->base, 2);
250                 src_fmt = 2;
251                 src_yuv_swap = 2;
252                 break;
253         case IEP_FORMAT_YCrCb_420_SP :
254                 IEP_REGB_SRC_FMT(iep_msg->base, 3);
255                 IEP_REGB_SRC_YUV_SWAP(iep_msg->base, 1);
256                 src_fmt = 3;
257                 src_yuv_swap = 1;
258                 break;
259         case IEP_FORMAT_YCrCb_420_P :
260                 IEP_REGB_SRC_FMT(iep_msg->base, 3);
261                 IEP_REGB_SRC_YUV_SWAP(iep_msg->base, 2);
262                 src_fmt = 3;
263                 src_yuv_swap = 2;
264                 break;
265         default:
266                 break;
267         }
268 #ifdef IEP_PRINT_INFO
269         IEP_DBG(" //==source data format config=================//\n\n");
270         IEP_DBG("sw_src_yuv_swap            = %d;//0:sp uv; 1:sp vu;"
271                 " 2:p ; 3:p;\n", src_yuv_swap);
272         IEP_DBG("sw_src_rgb_swap            = %d;//if ARGB 0:argb; 1,abgr;"
273                 " 2:rgba; 3:bgra; if rgb565: 0,2:rgb; 1,3:bgr;\n",
274                 src_rgb_swap);
275         IEP_DBG("sw_src_fmt                 = %d;//0:argb; 1:rgb565;"
276                 " 2:yuv422; 3:yuv420;\n\n", src_fmt);
277 #endif
278 }
279
280 static void iep_config_scl(struct IEP_MSG *iep_msg)
281 {
282         int scl_en;
283         int scl_sel;
284         //int vrt_fct;
285         //int hrz_fct;
286
287         unsigned int src_height, src_width, dst_height, dst_width;
288
289         int div_height_dst_src;
290         int div_width_dst_src;
291
292         src_height = iep_msg->src.act_h - 1;
293         src_width = iep_msg->src.act_w - 1;
294         dst_height = iep_msg->dst.act_h - 1;
295         dst_width = iep_msg->dst.act_w - 1;
296
297         if ((iep_msg->src.act_w == iep_msg->dst.act_w) &&
298             (iep_msg->src.act_h == iep_msg->dst.act_h))
299                 scl_en = 0;
300         else
301                 scl_en = 1;
302
303         if ((iep_msg->src.act_w >= iep_msg->dst.act_w) &&
304             (iep_msg->src.act_h >= iep_msg->dst.act_h))
305                 scl_sel = 0;
306         else if ((iep_msg->src.act_w >= iep_msg->dst.act_w) &&
307                  (iep_msg->src.act_h <= iep_msg->dst.act_h))
308                 scl_sel = 1;
309         else if ((iep_msg->src.act_w <= iep_msg->dst.act_w) &&
310                  (iep_msg->src.act_h >= iep_msg->dst.act_h))
311                 scl_sel = 2;
312         else
313                 scl_sel = 3;
314
315         //for vrt_fct
316         if ((scl_sel == 1) || (scl_sel == 3)) {
317                 div_height_dst_src = src_height * 65536 / dst_height;
318         } else {
319                 div_height_dst_src = (dst_height + 1) * 65536 /
320                         (src_height + 1);
321                 if ((div_height_dst_src * (src_height + 1)) <
322                     ((dst_height + 1) * 65536))
323                         div_height_dst_src = div_height_dst_src + 1;
324         }
325
326         if (div_height_dst_src == 65536)
327                 div_height_dst_src = 0;
328
329         //for hrz_fct
330         if ((scl_sel == 2) || (scl_sel == 3)) {
331                 div_width_dst_src = src_width * 65536 / dst_width;
332         } else {
333                 div_width_dst_src = (dst_width + 1) * 65536 / (src_width + 1);
334                 if ((div_width_dst_src * (src_width + 1)) <
335                     ((dst_width + 1) * 65536))
336                         div_width_dst_src = div_width_dst_src + 1;
337         }
338
339         if (div_width_dst_src == 65536)
340                 div_width_dst_src = 0;
341
342
343         IEP_REGB_SCL_EN(iep_msg->base, scl_en);
344
345         if (scl_en == 1) {
346                 IEP_REGB_SCL_SEL(iep_msg->base, scl_sel);
347                 IEP_REGB_SCL_UP_COE_SEL(iep_msg->base, iep_msg->scale_up_mode);
348                 IEP_REGB_SCL_VRT_FCT(iep_msg->base, div_height_dst_src);
349                 IEP_REGB_SCL_HRZ_FCT(iep_msg->base, div_width_dst_src);
350         }
351 #ifdef IEP_PRINT_INFO
352         IEP_DBG(" //==scaling config============================//\n\n");
353         IEP_DBG("sw_scl_en                  = %d;//0:disable; 1:enable;\n",
354                 scl_en);
355         IEP_DBG("sw_scl_sel                 = %d;//0:hrz down & vrt down;"
356                 "  1:hrz down & vrt up; 2:hrz up & vrt down;  3:hrz up &"
357                 " vrt up;\n", scl_sel);
358         IEP_DBG("sw_scl_up_coe_sel          = %d;//select four groups of"
359                 " up scaling coefficient\n", iep_msg->scale_up_mode);
360         IEP_DBG("sw_scl_vrt_fct             = %d;//if up-scaling,equal"
361                 " to floor(src_img_height/dst_image_height)*2^16;"
362                 " if down-scaling,equal to ceiling(dst_image_height/"
363                 "src_image_height)*2^16;\n", div_height_dst_src);
364         IEP_DBG("sw_scl_hrz_fct             = %d;//if up-scaling,equal"
365                 " to floor(src_img_widht/dst_image_width)*2^16;   if"
366                 " down-scaling,equal to ceiling(dst_image_width/"
367                 "src_image_width)*2^16  ; \n\n", div_width_dst_src);
368 #endif
369 }
370
371 static void iep_config_cg_order(struct IEP_MSG *iep_msg)
372 {
373         IEP_REGB_CON_GAM_ORDER(iep_msg->base,
374                 iep_msg->rgb_contrast_enhance_mode);
375 #ifdef IEP_PRINT_INFO
376         IEP_DBG(" //==rgb enhancement & denoise config==========//\n\n");
377         IEP_DBG("sw_con_gam_order           = %d;//0:CG(contrast/gamma"
378                 " operation)prior to DDE(de-noise/detail/edge enhance);"
379                 "  1:DDE prior to CG;\n",
380                 iep_msg->rgb_contrast_enhance_mode);
381 #endif
382 }
383
384 static void iep_config_cg(struct IEP_MSG *iep_msg)
385 {
386         unsigned i;
387         unsigned int cg_conf_addr;
388
389         IEP_REGB_RGB_CON_GAM_EN(iep_msg->base, iep_msg->rgb_cg_en);
390
391         if (iep_msg->rgb_cg_en) {
392                 cg_conf_addr = rIEP_CG_TAB_ADDR;
393
394                 for (i = 0; i < 192; i++) {
395                         WriteReg32(iep_msg->base, cg_conf_addr,
396                                 iep_msg->cg_tab[i]);
397                         cg_conf_addr += 0x04;
398                 }
399         }
400
401 #ifdef IEP_PRINT_INFO
402         IEP_DBG("sw_rgb_con_gam_en = 0;//0:contrast"
403                 " & gamma disable; 1:enable;\n",
404                 iep_msg->rgb_cg_en);
405 #endif
406 }
407
408 static void iep_config_dde(struct IEP_MSG *iep_msg)
409 {
410         IEP_REGB_RGB_ENH_SEL(iep_msg->base, iep_msg->rgb_enhance_mode);
411         IEP_REGB_ENH_THRESHOLD(iep_msg->base, iep_msg->enh_threshold);
412         IEP_REGB_ENH_ALPHA(iep_msg->base, iep_msg->enh_alpha);
413         IEP_REGB_ENH_RADIUS(iep_msg->base, iep_msg->enh_radius);
414 #ifdef IEP_PRINT_INFO
415         IEP_DBG("sw_rgb_enh_sel = %d;//0:no operation;"
416                 " 1:de-noise; 2:detail enhance; 3:edge enhance;\n",
417                 iep_msg->rgb_enhance_mode);
418 #endif
419
420 }
421
422 static void iep_config_color_enh(struct IEP_MSG *iep_msg)
423 {
424         IEP_REGB_RGB_COLOR_ENH_EN(iep_msg->base, iep_msg->rgb_color_enhance_en);
425         IEP_REGB_ENH_C_COE(iep_msg->base, iep_msg->rgb_enh_coe);
426 #ifdef IEP_PRINT_INFO
427         IEP_DBG("sw_rgb_color_enh_en = %d;//0:color enhance disable;"
428                 " 1:enable;\n\n",
429                 iep_msg->rgb_color_enhance_en);
430 #endif
431 }
432
433 static void iep_config_yuv_dns(struct IEP_MSG *iep_msg)
434 {
435         IEP_REGB_YUV_DNS_EN(iep_msg->base, iep_msg->yuv_3D_denoise_en);
436         IEP_REGB_YUV_DNS_LUMA_SPAT_SEL(iep_msg->base, 0);
437         IEP_REGB_YUV_DNS_LUMA_TEMP_SEL(iep_msg->base, 1);
438         IEP_REGB_YUV_DNS_CHROMA_SPAT_SEL(iep_msg->base, 2);
439         IEP_REGB_YUV_DNS_CHROMA_TEMP_SEL(iep_msg->base, 3);
440 #ifdef IEP_PRINT_INFO
441         IEP_DBG("//==yuv denoise config========================// \n\n");
442         IEP_DBG("sw_yuv_dns_en              = %d;//0:yuv 3d denoise disable;"
443                 " 1:enable\n\n", iep_msg->yuv_3D_denoise_en);
444 #endif
445 }
446
447
448 static void iep_config_dil(struct IEP_MSG *iep_msg)
449 {
450     int dein_mode;
451     switch (iep_msg->dein_mode) {
452     case IEP_DEINTERLACE_MODE_DISABLE:
453         dein_mode = dein_mode_bypass_dis;
454         break;
455     case IEP_DEINTERLACE_MODE_I2O1:
456         dein_mode = iep_msg->field_order == FIELD_ORDER_TOP_FIRST ? dein_mode_I2O1T : dein_mode_I2O1B;
457         break;
458     case IEP_DEINTERLACE_MODE_I4O1:
459 #if 1
460         dein_mode = iep_msg->field_order == FIELD_ORDER_TOP_FIRST ? dein_mode_I4O1B : dein_mode_I4O1T;
461 #else
462         dein_mode = iep_msg->field_order == FIELD_ORDER_TOP_FIRST ? dein_mode_I4O1T : dein_mode_I4O1B;
463 #endif
464         break;
465     case IEP_DEINTERLACE_MODE_I4O2:
466         dein_mode = dein_mode_I4O2;
467         break;
468     case IEP_DEINTERLACE_MODE_BYPASS:
469         dein_mode = dein_mode_bypass;
470         break;
471     default:
472         IEP_ERR("unknown deinterlace mode, set deinterlace mode (bypass)\n");
473         dein_mode = dein_mode_bypass;
474     }
475
476     IEP_REGB_DIL_MODE(iep_msg->base, dein_mode);
477     //hf
478     IEP_REGB_DIL_HF_EN(iep_msg->base, iep_msg->dein_high_fre_en);
479     if (iep_msg->dein_high_fre_en == 1) IEP_REGB_DIL_HF_FCT(iep_msg->base, iep_msg->dein_high_fre_fct);
480     //ei
481     IEP_REGB_DIL_EI_MODE(iep_msg->base, iep_msg->dein_ei_mode);
482     IEP_REGB_DIL_EI_SMOOTH(iep_msg->base, iep_msg->dein_ei_smooth);
483     IEP_REGB_DIL_EI_SEL(iep_msg->base, iep_msg->dein_ei_sel);
484     if (iep_msg->dein_ei_sel == 0) IEP_REGB_DIL_EI_RADIUS(iep_msg->base, iep_msg->dein_ei_radius);
485         IEP_REGB_DIL_MTN_TAB0(iep_msg->base, 0x40404040);
486         IEP_REGB_DIL_MTN_TAB1(iep_msg->base, 0x3c3e3f3f);
487         IEP_REGB_DIL_MTN_TAB2(iep_msg->base, 0x3336393b);
488         IEP_REGB_DIL_MTN_TAB3(iep_msg->base, 0x272a2d31);
489         IEP_REGB_DIL_MTN_TAB4(iep_msg->base, 0x181c2023);
490         IEP_REGB_DIL_MTN_TAB5(iep_msg->base, 0x0c0e1215);
491         IEP_REGB_DIL_MTN_TAB6(iep_msg->base, 0x03040609);
492         IEP_REGB_DIL_MTN_TAB7(iep_msg->base, 0x00000001);
493 }
494
495 static void iep_config_yuv_enh(struct IEP_MSG *iep_msg)
496 {
497         IEP_REGB_YUV_ENH_EN(iep_msg->base, iep_msg->yuv_enhance_en);
498         if (iep_msg->yuv_enhance_en == 1) {
499                 IEP_REGB_VIDEO_MODE(iep_msg->base, iep_msg->video_mode);
500                 if (iep_msg->video_mode == normal_mode) {
501                         IEP_REGB_SAT_CON(iep_msg->base, iep_msg->sat_con_int);
502                         IEP_REGB_CONTRAST(iep_msg->base,
503                                 iep_msg->contrast_int);
504                         IEP_REGB_BRIGHTNESS(iep_msg->base,
505                                 iep_msg->yuv_enh_brightness);
506                         IEP_REGB_COS_HUE(iep_msg->base, iep_msg->cos_hue_int);
507                         IEP_REGB_SIN_HUE(iep_msg->base, iep_msg->sin_hue_int);
508                 } else if (iep_msg->video_mode == color_bar) { //color bar
509                         IEP_REGB_COLOR_BAR_Y(iep_msg->base,
510                                 iep_msg->color_bar_y);
511                         IEP_REGB_COLOR_BAR_U(iep_msg->base,
512                                 iep_msg->color_bar_u);
513                         IEP_REGB_COLOR_BAR_V(iep_msg->base,
514                                 iep_msg->color_bar_v);
515                 }
516
517         }
518 }
519
520 static void iep_config_rgb2yuv(struct IEP_MSG *iep_msg)
521 {
522         unsigned char cond1, cond2;
523         unsigned int rgb2yuv_en = 0;
524
525         //rgb in,yuv out
526         cond1 = ((iep_msg->src.format <= 5) && (iep_msg->dst.format > 5)) ?
527                 1 : 0;
528
529         //rgb process,yuv out
530         cond2 = (((iep_msg->rgb_color_enhance_en == 1) ||
531                   (iep_msg->rgb_cg_en == 1) ||
532                   (iep_msg->rgb_enhance_mode != rgb_enhance_bypass)) &&
533                  (iep_msg->dst.format > 5)) ? 1 : 0;
534
535
536         if ((cond1 == 1) || (cond2 == 1)) {
537                 IEP_REGB_RGB_TO_YUV_EN(iep_msg->base, 1);
538                 rgb2yuv_en = 1;
539                 IEP_REGB_RGB2YUV_COE_SEL(iep_msg->base, iep_msg->rgb2yuv_mode);
540                 IEP_REGB_RGB2YUV_INPUT_CLIP(iep_msg->base,
541                         iep_msg->rgb2yuv_clip_en);
542         } else
543                 IEP_REGB_RGB_TO_YUV_EN(iep_msg->base, 0);
544 #ifdef IEP_PRINT_INFO
545         IEP_DBG("//==color space conversion config============//\n\n");
546         IEP_DBG("sw_rgb_to_yuv_en = %d;\n", rgb2yuv_en);
547         IEP_DBG("sw_rgb2yuv_coe_sel = %d;\n", iep_msg->rgb2yuv_mode);
548         IEP_DBG("sw_rgb2yuv_input_clip = %d;\n\n", iep_msg->rgb2yuv_clip_en);
549 #endif
550
551 }
552
553 static void iep_config_yuv2rgb(struct IEP_MSG *iep_msg)
554 {
555         unsigned char cond1, cond2;
556         unsigned int yuv2rgb_en = 0;
557
558         //yuv in,rgb out
559         cond1 = ((iep_msg->src.format > 5) &&
560                  (iep_msg->dst.format <= 5)) ? 1 : 0;
561
562         //yuv in,rgb process
563         cond2 = (((iep_msg->rgb_color_enhance_en == 1) ||
564                   (iep_msg->rgb_cg_en == 1) ||
565                   (iep_msg->rgb_enhance_mode != rgb_enhance_bypass)) &&
566                  (iep_msg->src.format > 5)) ? 1 : 0;
567
568         if ((cond1 == 1) || (cond2 == 1)) {
569                 IEP_REGB_YUV_TO_RGB_EN(iep_msg->base, 1);
570                 yuv2rgb_en = 1;
571                 IEP_REGB_YUV2RGB_COE_SEL(iep_msg->base,
572                         iep_msg->yuv2rgb_mode);
573                 IEP_REGB_YUV2RGB_INPUT_CLIP(iep_msg->base,
574                         iep_msg->yuv2rgb_clip_en);
575         } else {
576                 IEP_REGB_YUV_TO_RGB_EN(iep_msg->base, 0);
577         }
578 #ifdef IEP_PRINT_INFO
579         IEP_DBG("sw_yuv_to_rgb_en           = %d;\n", yuv2rgb_en);
580         IEP_DBG("sw_yuv2rgb_coe_sel         = %d;\n", iep_msg->yuv2rgb_mode);
581         IEP_DBG("sw_yuv2rgb_input_clip = %d;\n\n", iep_msg->yuv2rgb_clip_en);
582 #endif
583 }
584
585 static void iep_config_dither_up(struct IEP_MSG *iep_msg)
586 {
587         unsigned int dither_up = 0;
588         if ((iep_msg->src.format == IEP_FORMAT_RGB_565) ||
589             (iep_msg->src.format == IEP_FORMAT_BGR_565)) {
590                 IEP_REGB_DITHER_UP_EN(iep_msg->base, iep_msg->dither_up_en);
591                 dither_up = iep_msg->dither_up_en;
592         } else {
593                 IEP_REGB_DITHER_UP_EN(iep_msg->base, 0);
594         }
595 #ifdef IEP_PRINT_INFO
596         IEP_DBG("//==dither config=============================//\n\n");
597         IEP_DBG("sw_dither_up_en            = %d;\n", dither_up);
598 #endif
599 }
600
601 static void iep_config_dither_down(struct IEP_MSG *iep_msg)
602 {
603         unsigned int dither_down = 0;
604         if ((iep_msg->dst.format == IEP_FORMAT_RGB_565) ||
605             (iep_msg->dst.format == IEP_FORMAT_BGR_565)) {
606                 IEP_REGB_DITHER_DOWN_EN(iep_msg->base, 1);
607                 dither_down = 1;
608         } else {
609                 IEP_REGB_DITHER_DOWN_EN(iep_msg->base, 0);
610         }
611 #ifdef IEP_PRINT_INFO
612         IEP_DBG("sw_dither_down_en = %d;\n\n", dither_down);
613 #endif
614 }
615
616 static void iep_config_glb_alpha(struct IEP_MSG *iep_msg)
617 {
618         IEP_REGB_GLB_ALPHA(iep_msg->base, iep_msg->global_alpha_value);
619 #ifdef IEP_PRINT_INFO
620         IEP_DBG("//==global alpha for ARGB config=============//\n\n");
621         IEP_DBG("sw_glb_alpha = %d;//global alpha value for output ARGB\n\n",
622                 iep_msg->global_alpha_value);
623 #endif
624 }
625
626 static void iep_config_vir_line(struct IEP_MSG *iep_msg)
627 {
628         unsigned int src_vir_w;
629         unsigned int dst_vir_w;
630
631         switch (iep_msg->src.format) {
632         case IEP_FORMAT_ARGB_8888 :
633                 src_vir_w = iep_msg->src.vir_w;
634                 break;
635         case IEP_FORMAT_ABGR_8888 :
636                 src_vir_w = iep_msg->src.vir_w;
637                 break;
638         case IEP_FORMAT_RGBA_8888 :
639                 src_vir_w = iep_msg->src.vir_w;
640                 break;
641         case IEP_FORMAT_BGRA_8888 :
642                 src_vir_w = iep_msg->src.vir_w;
643                 break;
644         case IEP_FORMAT_RGB_565 :
645                 if (iep_msg->src.vir_w % 2 == 1)
646                         src_vir_w = (iep_msg->src.vir_w + 1) / 2;
647                 else
648                         src_vir_w = iep_msg->src.vir_w / 2;
649                 break;
650         case IEP_FORMAT_BGR_565 :
651                 if (iep_msg->src.vir_w % 2 == 1)
652                         src_vir_w = iep_msg->src.vir_w / 2 + 1;
653                 else
654                         src_vir_w = iep_msg->src.vir_w / 2;
655                 break;
656         case IEP_FORMAT_YCbCr_422_SP :
657                 if (iep_msg->src.vir_w % 4 != 0)
658                         src_vir_w = iep_msg->src.vir_w / 4 + 1;
659                 else
660                         src_vir_w = iep_msg->src.vir_w / 4;
661                 break;
662         case IEP_FORMAT_YCbCr_422_P :
663                 if (iep_msg->src.vir_w % 4 != 0)
664                         src_vir_w = iep_msg->src.vir_w / 4 + 1;
665                 else
666                         src_vir_w = iep_msg->src.vir_w / 4;
667                 break;
668         case IEP_FORMAT_YCbCr_420_SP :
669                 if (iep_msg->src.vir_w % 4 != 0)
670                         src_vir_w = iep_msg->src.vir_w / 4 + 1;
671                 else
672                         src_vir_w = iep_msg->src.vir_w / 4;
673                 break;
674         case IEP_FORMAT_YCbCr_420_P :
675                 if (iep_msg->src.vir_w % 4 != 0)
676                         src_vir_w = iep_msg->src.vir_w / 4 + 1;
677                 else
678                         src_vir_w = iep_msg->src.vir_w / 4;
679                 break;
680         case IEP_FORMAT_YCrCb_422_SP :
681                 if (iep_msg->src.vir_w % 4 != 0)
682                         src_vir_w = iep_msg->src.vir_w / 4 + 1;
683                 else
684                         src_vir_w = iep_msg->src.vir_w / 4;
685                 break;
686         case IEP_FORMAT_YCrCb_422_P :
687                 if (iep_msg->src.vir_w % 4 != 0)
688                         src_vir_w = iep_msg->src.vir_w / 4 + 1;
689                 else
690                         src_vir_w = iep_msg->src.vir_w / 4;
691                 break;
692         case IEP_FORMAT_YCrCb_420_SP :
693                 if (iep_msg->src.vir_w % 4 != 0)
694                         src_vir_w = iep_msg->src.vir_w / 4 + 1;
695                 else
696                         src_vir_w = iep_msg->src.vir_w / 4;
697                 break;
698         case IEP_FORMAT_YCrCb_420_P :
699                 if (iep_msg->src.vir_w % 4 != 0)
700                         src_vir_w = iep_msg->src.vir_w / 4 + 1;
701                 else
702                         src_vir_w = iep_msg->src.vir_w / 4;
703                 break;
704         default:
705                 IEP_ERR("Unkown format,"
706                         "set the source image virtual width 0\n");
707                 src_vir_w = 0;
708                 break;
709         }
710
711         switch (iep_msg->dst.format) {
712         case IEP_FORMAT_ARGB_8888 :
713                 dst_vir_w = iep_msg->dst.vir_w;
714                 break;
715         case IEP_FORMAT_ABGR_8888 :
716                 dst_vir_w = iep_msg->dst.vir_w;
717                 break;
718         case IEP_FORMAT_RGBA_8888 :
719                 dst_vir_w = iep_msg->dst.vir_w;
720                 break;
721         case IEP_FORMAT_BGRA_8888 :
722                 dst_vir_w = iep_msg->dst.vir_w;
723                 break;
724         case IEP_FORMAT_RGB_565 :
725                 if (iep_msg->dst.vir_w % 2 == 1)
726                         dst_vir_w = (iep_msg->dst.vir_w + 1) / 2;
727                 else
728                         dst_vir_w = iep_msg->dst.vir_w / 2;
729                 break;
730         case IEP_FORMAT_BGR_565 :
731                 if (iep_msg->dst.vir_w % 2 == 1)
732                         dst_vir_w = iep_msg->dst.vir_w / 2 + 1;
733                 else
734                         dst_vir_w = iep_msg->dst.vir_w / 2;
735                 break;
736         case IEP_FORMAT_YCbCr_422_SP :
737                 if (iep_msg->dst.vir_w % 4 != 0)
738                         dst_vir_w = iep_msg->dst.vir_w / 4 + 1;
739                 else
740                         dst_vir_w = iep_msg->dst.vir_w / 4;
741                 break;
742         case IEP_FORMAT_YCbCr_422_P :
743                 if (iep_msg->dst.vir_w % 4 != 0)
744                         dst_vir_w = iep_msg->dst.vir_w / 4 + 1;
745                 else
746                         dst_vir_w = iep_msg->dst.vir_w / 4;
747                 break;
748         case IEP_FORMAT_YCbCr_420_SP :
749                 if (iep_msg->dst.vir_w % 4 != 0)
750                         dst_vir_w = iep_msg->dst.vir_w / 4 + 1;
751                 else
752                         dst_vir_w = iep_msg->dst.vir_w / 4;
753                 break;
754         case IEP_FORMAT_YCbCr_420_P :
755                 if (iep_msg->dst.vir_w % 4 != 0)
756                         dst_vir_w = iep_msg->dst.vir_w / 4 + 1;
757                 else
758                         dst_vir_w = iep_msg->dst.vir_w / 4;
759                 break;
760         case IEP_FORMAT_YCrCb_422_SP :
761                 if (iep_msg->dst.vir_w % 4 != 0)
762                         dst_vir_w = iep_msg->dst.vir_w / 4 + 1;
763                 else
764                         dst_vir_w = iep_msg->dst.vir_w / 4;
765                 break;
766         case IEP_FORMAT_YCrCb_422_P :
767                 if (iep_msg->dst.vir_w % 4 != 0)
768                         dst_vir_w = iep_msg->dst.vir_w / 4 + 1;
769                 else
770                         dst_vir_w = iep_msg->dst.vir_w / 4;
771                 break;
772         case IEP_FORMAT_YCrCb_420_SP :
773                 if (iep_msg->dst.vir_w % 4 != 0)
774                         dst_vir_w = iep_msg->dst.vir_w / 4 + 1;
775                 else
776                         dst_vir_w = iep_msg->dst.vir_w / 4;
777                 break;
778         case IEP_FORMAT_YCrCb_420_P :
779                 if (iep_msg->dst.vir_w % 4 != 0)
780                         dst_vir_w = iep_msg->dst.vir_w / 4 + 1;
781                 else
782                         dst_vir_w = iep_msg->dst.vir_w / 4;
783                 break;
784         default:
785                 IEP_ERR("Unkown format, set the destination"
786                         " image virtual width 0\n");
787                 dst_vir_w = 0;
788                 break;
789         }
790         IEP_REGB_DST_VIR_LINE_WIDTH(iep_msg->base, dst_vir_w);
791         IEP_REGB_SRC_VIR_LINE_WIDTH(iep_msg->base, src_vir_w);
792 }
793
794 static void iep_config_src_addr(struct IEP_MSG *iep_msg)
795 {
796         u32 src_addr_yrgb;
797         u32 src_addr_cbcr;
798         u32 src_addr_cr;
799         u32 src_addr_y1;
800         u32 src_addr_cbcr1;
801         u32 src_addr_cr1;
802         u32 src_addr_y_itemp;
803         u32 src_addr_cbcr_itemp;
804         u32 src_addr_cr_itemp;
805         u32 src_addr_y_ftemp;
806         u32 src_addr_cbcr_ftemp;
807         u32 src_addr_cr_ftemp;
808         unsigned int offset_addr_y = 0;
809         unsigned int offset_addr_uv = 0;
810         unsigned int offset_addr_v = 0;
811         //unsigned int offset_addr_y_w = 0;
812         unsigned int offset_addr_uv_w = 0;
813         unsigned int offset_addr_v_w = 0;
814         //unsigned int offset_addr_y_h = 0;
815         unsigned int offset_addr_uv_h = 0;
816         unsigned int offset_addr_v_h = 0;
817
818         unsigned int offset_x_equ_uv;
819         unsigned int offset_x_u_byte;
820         unsigned int offset_x_v_byte;
821         unsigned int vir_w_euq_uv;
822         unsigned int line_u_byte;
823         unsigned int line_v_byte;
824         unsigned int offset_y_equ_420_uv = 0;
825
826         //**********************************************//
827         //***********y addr offset**********************//
828         //**********************************************//
829         if (iep_msg->src.format <= 3) {
830                 offset_addr_y = iep_msg->src.y_off * 4 *
831                         iep_msg->src.vir_w + iep_msg->src.x_off * 4;
832         } else if (iep_msg->src.format <= 5) {
833                 offset_addr_y = iep_msg->src.y_off * 2 *
834                         iep_msg->src.vir_w + iep_msg->src.x_off * 2;
835         } else {
836                 offset_addr_y = iep_msg->src.y_off *
837                         iep_msg->src.vir_w + iep_msg->src.x_off;
838         }
839
840         //**********************************************//
841         //***********uv addr offset*********************//
842         //**********************************************//
843         // note: image size align to even when image format is yuv
844
845         //----------offset_w--------//
846         if (iep_msg->src.x_off % 2 == 1)
847                 offset_x_equ_uv = iep_msg->src.x_off + 1;
848         else
849                 offset_x_equ_uv = iep_msg->src.x_off;
850
851         offset_x_u_byte = offset_x_equ_uv / 2;
852         offset_x_v_byte = offset_x_equ_uv / 2;
853
854         if ((iep_msg->src.format == IEP_FORMAT_YCbCr_422_SP) ||
855             (iep_msg->src.format == IEP_FORMAT_YCbCr_420_SP)
856                 || (iep_msg->src.format == IEP_FORMAT_YCrCb_422_SP) ||
857             (iep_msg->src.format == IEP_FORMAT_YCrCb_420_SP))
858                 offset_addr_uv_w = offset_x_u_byte + offset_x_v_byte;
859         else {
860                 offset_addr_uv_w = offset_x_u_byte;
861                 offset_addr_v_w = offset_x_v_byte;
862         }
863
864         //----------offset_h--------//
865         if (iep_msg->src.vir_w % 2 == 1)
866                 vir_w_euq_uv = iep_msg->src.vir_w + 1;
867         else
868                 vir_w_euq_uv = iep_msg->src.vir_w;
869
870         line_u_byte = vir_w_euq_uv / 2;
871         line_v_byte = vir_w_euq_uv / 2;
872
873         if (iep_msg->src.y_off % 2 == 1)
874                 offset_y_equ_420_uv = iep_msg->src.y_off + 1;
875         else
876                 offset_y_equ_420_uv = iep_msg->src.y_off;
877
878         switch (iep_msg->src.format) {
879         case IEP_FORMAT_YCbCr_422_SP :
880                 offset_addr_uv_h = (line_u_byte + line_v_byte) *
881                         iep_msg->src.y_off;
882                 break;
883         case IEP_FORMAT_YCbCr_422_P :
884                 offset_addr_uv_h = line_u_byte * iep_msg->src.y_off;
885                 offset_addr_v_h = line_v_byte * iep_msg->src.y_off;
886                 break;
887         case IEP_FORMAT_YCbCr_420_SP :
888                 offset_addr_uv_h = (line_u_byte + line_v_byte) *
889                         offset_y_equ_420_uv / 2;
890                 break;
891         case IEP_FORMAT_YCbCr_420_P :
892                 offset_addr_uv_h = line_u_byte * offset_y_equ_420_uv / 2;
893                 offset_addr_v_h = line_v_byte * offset_y_equ_420_uv / 2;
894                 break;
895         case IEP_FORMAT_YCrCb_422_SP :
896                 offset_addr_uv_h = (line_u_byte + line_v_byte) *
897                         iep_msg->src.y_off;
898                 break;
899         case IEP_FORMAT_YCrCb_422_P :
900                 offset_addr_uv_h = line_u_byte * iep_msg->src.y_off;
901                 offset_addr_v_h = line_v_byte * iep_msg->src.y_off;
902                 break;
903         case IEP_FORMAT_YCrCb_420_SP :
904                 offset_addr_uv_h = (line_u_byte + line_v_byte) *
905                         offset_y_equ_420_uv / 2;
906                 break;
907         case IEP_FORMAT_YCrCb_420_P :
908                 offset_addr_uv_h = line_u_byte * offset_y_equ_420_uv / 2;
909                 offset_addr_v_h = line_v_byte * offset_y_equ_420_uv / 2;
910                 break;
911         default:
912                 break;
913         }
914         //----------offset u/v addr--------//
915
916         offset_addr_uv = offset_addr_uv_w + offset_addr_uv_h;
917         offset_addr_v  = offset_addr_v_w + offset_addr_v_h;
918         //**********************************************//
919         //***********yuv address   *********************//
920         //**********************************************//
921         if (iep_service.iommu_dev == NULL) {
922                 src_addr_yrgb = ((u32)iep_msg->src.mem_addr) + offset_addr_y;
923                 src_addr_cbcr = ((u32)iep_msg->src.uv_addr) + offset_addr_uv;
924                 src_addr_cr = ((u32)iep_msg->src.v_addr) + offset_addr_v;
925
926                 src_addr_y1 = ((u32)iep_msg->src1.mem_addr) + offset_addr_y;
927                 src_addr_cbcr1 = ((u32)iep_msg->src1.uv_addr) + offset_addr_uv;
928                 src_addr_cr1 = ((u32)iep_msg->src1.v_addr) + offset_addr_v;
929
930                 src_addr_y_itemp = ((u32)iep_msg->src_itemp.mem_addr) +
931                         offset_addr_y;
932                 src_addr_cbcr_itemp = ((u32)iep_msg->src_itemp.uv_addr) +
933                         offset_addr_uv;
934                 src_addr_cr_itemp = ((u32)iep_msg->src_itemp.v_addr) +
935                         offset_addr_v;
936
937                 src_addr_y_ftemp = ((u32)iep_msg->src_ftemp.mem_addr) +
938                         offset_addr_y;
939                 src_addr_cbcr_ftemp = ((u32)iep_msg->src_ftemp.uv_addr) +
940                         offset_addr_uv;
941                 src_addr_cr_ftemp = ((u32)iep_msg->src_ftemp.v_addr) +
942                         offset_addr_v;
943         } else {
944                 src_addr_yrgb = ((u32)iep_msg->src.mem_addr) + (offset_addr_y << 10);
945                 src_addr_cbcr = ((u32)iep_msg->src.uv_addr) + (offset_addr_uv << 10);
946                 src_addr_cr = ((u32)iep_msg->src.v_addr) + (offset_addr_v << 10);
947
948                 src_addr_y1 = ((u32)iep_msg->src1.mem_addr) + (offset_addr_y << 10);
949                 src_addr_cbcr1 = ((u32)iep_msg->src1.uv_addr) + (offset_addr_uv  << 10);
950                 src_addr_cr1 = ((u32)iep_msg->src1.v_addr) + (offset_addr_v << 10);
951
952                 src_addr_y_itemp = ((u32)iep_msg->src_itemp.mem_addr) +
953                         (offset_addr_y << 10);
954                 src_addr_cbcr_itemp = ((u32)iep_msg->src_itemp.uv_addr) +
955                         (offset_addr_uv << 10);
956                 src_addr_cr_itemp = ((u32)iep_msg->src_itemp.v_addr) +
957                         (offset_addr_v << 10);
958
959                 src_addr_y_ftemp = ((u32)iep_msg->src_ftemp.mem_addr) +
960                         (offset_addr_y << 10);
961                 src_addr_cbcr_ftemp = ((u32)iep_msg->src_ftemp.uv_addr) +
962                         (offset_addr_uv << 10);
963                 src_addr_cr_ftemp = ((u32)iep_msg->src_ftemp.v_addr) +
964                         (offset_addr_v << 10);
965         }
966
967         if ((iep_msg->dein_mode == IEP_DEINTERLACE_MODE_I4O1 ||
968              iep_msg->dein_mode == IEP_DEINTERLACE_MODE_I4O2) &&
969 #if 1
970                 iep_msg->field_order == FIELD_ORDER_BOTTOM_FIRST
971 #else
972                 iep_msg->field_order == FIELD_ORDER_TOP_FIRST
973 #endif
974                 ) {
975                 IEP_REGB_SRC_ADDR_YRGB(iep_msg->base, src_addr_y1);
976                 IEP_REGB_SRC_ADDR_CBCR(iep_msg->base, src_addr_cbcr1);
977                 IEP_REGB_SRC_ADDR_CR(iep_msg->base, src_addr_cr1);
978                 IEP_REGB_SRC_ADDR_Y1(iep_msg->base, src_addr_yrgb);
979                 IEP_REGB_SRC_ADDR_CBCR1(iep_msg->base, src_addr_cbcr);
980                 IEP_REGB_SRC_ADDR_CR1(iep_msg->base, src_addr_cr);
981         } else {
982                 IEP_REGB_SRC_ADDR_YRGB(iep_msg->base, src_addr_yrgb);
983                 IEP_REGB_SRC_ADDR_CBCR(iep_msg->base, src_addr_cbcr);
984                 IEP_REGB_SRC_ADDR_CR(iep_msg->base, src_addr_cr);
985                 IEP_REGB_SRC_ADDR_Y1(iep_msg->base, src_addr_y1);
986                 IEP_REGB_SRC_ADDR_CBCR1(iep_msg->base, src_addr_cbcr1);
987                 IEP_REGB_SRC_ADDR_CR1(iep_msg->base, src_addr_cr1);
988         }
989
990         if (iep_msg->yuv_3D_denoise_en) {
991                 IEP_REGB_SRC_ADDR_Y_ITEMP(iep_msg->base,
992                         src_addr_y_itemp);
993                 IEP_REGB_SRC_ADDR_CBCR_ITEMP(iep_msg->base,
994                         src_addr_cbcr_itemp);
995                 IEP_REGB_SRC_ADDR_Y_FTEMP(iep_msg->base,
996                         src_addr_y_ftemp);
997                 IEP_REGB_SRC_ADDR_CBCR_FTEMP(iep_msg->base,
998                         src_addr_cbcr_ftemp);
999                 if ((iep_msg->src.format == IEP_FORMAT_YCbCr_422_P) ||
1000                     (iep_msg->src.format == IEP_FORMAT_YCbCr_420_P)
1001                         || (iep_msg->src.format == IEP_FORMAT_YCrCb_422_P) ||
1002                     (iep_msg->src.format == IEP_FORMAT_YCrCb_420_P)) {
1003                         IEP_REGB_SRC_ADDR_CR_ITEMP(iep_msg->base,
1004                                 src_addr_cr_itemp);
1005                         IEP_REGB_SRC_ADDR_CR_FTEMP(iep_msg->base,
1006                                 src_addr_cr_ftemp);
1007                 }
1008         }
1009 #ifdef IEP_PRINT_INFO
1010         IEP_DBG("//-------source address for image-------// \n\n");
1011         IEP_DBG("sw_src_addr_yrgb           = 32'h%x;\n", src_addr_yrgb);
1012         IEP_DBG("sw_src_addr_cbcr           = 32'h%x;\n", src_addr_cbcr);
1013         IEP_DBG("sw_src_addr_cr             = 32'h%x;\n", src_addr_cr);
1014         IEP_DBG("sw_src_addr_y1             = 32'h%x;\n", src_addr_y1);
1015         IEP_DBG("sw_src_addr_cbcr0          = 32'h%x;\n", src_addr_cbcr1);
1016         IEP_DBG("sw_src_addr_cr0            = 32'h%x;\n", src_addr_cr1);
1017         IEP_DBG("sw_src_addr_y_itemp        = 32'h%x;\n", src_addr_y_itemp);
1018         IEP_DBG("sw_src_addr_cbcr_itemp     = 32'h%x;\n", src_addr_cbcr_itemp);
1019         IEP_DBG("sw_src_addr_cr_itemp       = 32'h%x;\n", src_addr_cr_itemp);
1020         IEP_DBG("sw_src_addr_y_ftemp        = 32'h%x;\n", src_addr_y_ftemp);
1021         IEP_DBG("sw_src_addr_cbcr_ftemp     = 32'h%x;\n", src_addr_cbcr_ftemp);
1022         IEP_DBG("sw_src_addr_cr_ftemp       = 32'h%x;\n\n", src_addr_cr_ftemp);
1023 #endif
1024 }
1025
1026 static void iep_config_dst_addr(struct IEP_MSG *iep_msg)
1027 {
1028         u32 dst_addr_yrgb;
1029         u32 dst_addr_cbcr;
1030         u32 dst_addr_cr;
1031         u32 dst_addr_y1;
1032         u32 dst_addr_cbcr1;
1033         u32 dst_addr_cr1;
1034         u32 dst_addr_y_itemp;
1035         u32 dst_addr_cbcr_itemp;
1036         u32 dst_addr_cr_itemp;
1037         u32 dst_addr_y_ftemp;
1038         u32 dst_addr_cbcr_ftemp;
1039         u32 dst_addr_cr_ftemp;
1040         unsigned int offset_addr_y = 0;
1041         unsigned int offset_addr_uv = 0;
1042         unsigned int offset_addr_v = 0;
1043         //unsigned int offset_addr_y_w = 0;
1044         unsigned int offset_addr_uv_w = 0;
1045         unsigned int offset_addr_v_w = 0;
1046         //unsigned int offset_addr_y_h = 0;
1047         unsigned int offset_addr_uv_h = 0;
1048         unsigned int offset_addr_v_h = 0;
1049
1050         unsigned int offset_x_equ_uv;
1051         unsigned int offset_x_u_byte;
1052         unsigned int offset_x_v_byte;
1053         unsigned int vir_w_euq_uv;
1054         unsigned int line_u_byte;
1055         unsigned int line_v_byte;
1056         unsigned int offset_y_equ_420_uv = 0;
1057
1058         //**********************************************//
1059         //***********y addr offset**********************//
1060         //**********************************************//
1061         if (iep_msg->dst.format <= 3) {
1062                 offset_addr_y = iep_msg->dst.y_off * 4 *
1063                         iep_msg->dst.vir_w + iep_msg->dst.x_off * 4;
1064         } else if (iep_msg->dst.format <= 5) {
1065                 offset_addr_y = iep_msg->dst.y_off * 2 *
1066                         iep_msg->dst.vir_w + iep_msg->dst.x_off * 2;
1067         } else {
1068                 offset_addr_y = iep_msg->dst.y_off *
1069                         iep_msg->dst.vir_w + iep_msg->dst.x_off;
1070         }
1071
1072         //**********************************************//
1073         //***********uv addr offset*********************//
1074         //**********************************************//
1075         // note: image size align to even when image format is yuv
1076
1077         //----------offset_w--------//
1078         if (iep_msg->dst.x_off % 2 == 1)
1079                 offset_x_equ_uv = iep_msg->dst.x_off + 1;
1080         else
1081                 offset_x_equ_uv = iep_msg->dst.x_off;
1082
1083         offset_x_u_byte = offset_x_equ_uv / 2;
1084         offset_x_v_byte = offset_x_equ_uv / 2;
1085
1086         if ((iep_msg->dst.format == IEP_FORMAT_YCbCr_422_SP) ||
1087             (iep_msg->dst.format == IEP_FORMAT_YCbCr_420_SP)
1088                 || (iep_msg->dst.format == IEP_FORMAT_YCrCb_422_SP) ||
1089             (iep_msg->dst.format == IEP_FORMAT_YCrCb_420_SP))
1090                 offset_addr_uv_w = offset_x_u_byte + offset_x_v_byte;
1091         else {
1092                 offset_addr_uv_w = offset_x_u_byte;
1093                 offset_addr_v_w = offset_x_v_byte;
1094         }
1095
1096         //----------offset_h--------//
1097         if (iep_msg->dst.vir_w % 2 == 1)
1098                 vir_w_euq_uv = iep_msg->dst.vir_w + 1;
1099         else
1100                 vir_w_euq_uv = iep_msg->dst.vir_w;
1101
1102         line_u_byte = vir_w_euq_uv / 2;
1103         line_v_byte = vir_w_euq_uv / 2;
1104
1105         if (iep_msg->dst.y_off % 2 == 1)
1106                 offset_y_equ_420_uv = iep_msg->dst.y_off + 1;
1107         else
1108                 offset_y_equ_420_uv = iep_msg->dst.y_off;
1109
1110         switch (iep_msg->dst.format) {
1111         case IEP_FORMAT_YCbCr_422_SP :
1112                 offset_addr_uv_h = (line_u_byte + line_v_byte) *
1113                         iep_msg->dst.y_off;
1114                 break;
1115         case IEP_FORMAT_YCbCr_422_P :
1116                 offset_addr_uv_h = line_u_byte * iep_msg->dst.y_off;
1117                 offset_addr_v_h = line_v_byte * iep_msg->dst.y_off;
1118                 break;
1119         case IEP_FORMAT_YCbCr_420_SP :
1120                 offset_addr_uv_h = (line_u_byte + line_v_byte) *
1121                         offset_y_equ_420_uv / 2;
1122                 break;
1123         case IEP_FORMAT_YCbCr_420_P :
1124                 offset_addr_uv_h = line_u_byte * offset_y_equ_420_uv / 2;
1125                 offset_addr_v_h = line_v_byte * offset_y_equ_420_uv / 2;
1126                 break;
1127         case IEP_FORMAT_YCrCb_422_SP :
1128                 offset_addr_uv_h = (line_u_byte + line_v_byte) *
1129                         iep_msg->dst.y_off;
1130                 break;
1131         case IEP_FORMAT_YCrCb_422_P :
1132                 offset_addr_uv_h = line_u_byte * iep_msg->dst.y_off;
1133                 offset_addr_v_h = line_v_byte * iep_msg->dst.y_off;
1134                 break;
1135         case IEP_FORMAT_YCrCb_420_SP :
1136                 offset_addr_uv_h = (line_u_byte + line_v_byte) *
1137                         offset_y_equ_420_uv / 2;
1138                 break;
1139         case IEP_FORMAT_YCrCb_420_P :
1140                 offset_addr_uv_h = line_u_byte * offset_y_equ_420_uv / 2;
1141                 offset_addr_v_h = line_v_byte * offset_y_equ_420_uv / 2;
1142                 break;
1143         default:
1144                 break;
1145         }
1146         //----------offset u/v addr--------//
1147
1148         offset_addr_uv = offset_addr_uv_w + offset_addr_uv_h;
1149         offset_addr_v  = offset_addr_v_w + offset_addr_v_h;
1150         //**********************************************//
1151         //***********yuv address   *********************//
1152         //**********************************************//
1153
1154         if (iep_service.iommu_dev == NULL) {
1155                 dst_addr_yrgb = ((u32)iep_msg->dst.mem_addr) + offset_addr_y;
1156                 dst_addr_cbcr = ((u32)iep_msg->dst.uv_addr) + offset_addr_uv;
1157                 dst_addr_cr = ((u32)iep_msg->dst.v_addr) + offset_addr_v;
1158
1159                 // former frame when processing deinterlace
1160                 dst_addr_y1 = ((u32)iep_msg->dst1.mem_addr) + offset_addr_y;
1161                 dst_addr_cbcr1 = ((u32)iep_msg->dst1.uv_addr) + offset_addr_uv;
1162                 dst_addr_cr1 = ((u32)iep_msg->dst1.v_addr) + offset_addr_v;
1163
1164                 dst_addr_y_itemp = ((u32)iep_msg->dst_itemp.mem_addr) +
1165                         offset_addr_y;
1166                 dst_addr_cbcr_itemp = ((u32)iep_msg->dst_itemp.uv_addr) +
1167                         offset_addr_uv;
1168                 dst_addr_cr_itemp = ((u32)iep_msg->dst_itemp.v_addr) +
1169                         offset_addr_v;
1170
1171                 dst_addr_y_ftemp = ((u32)iep_msg->dst_ftemp.mem_addr) +
1172                         offset_addr_y;
1173                 dst_addr_cbcr_ftemp = ((u32)iep_msg->dst_ftemp.uv_addr) +
1174                         offset_addr_uv;
1175                 dst_addr_cr_ftemp = ((u32)iep_msg->dst_ftemp.v_addr) +
1176                         offset_addr_v;
1177         } else {
1178                 dst_addr_yrgb = ((u32)iep_msg->dst.mem_addr) + (offset_addr_y << 10);
1179                 dst_addr_cbcr = ((u32)iep_msg->dst.uv_addr) + (offset_addr_uv << 10);
1180                 dst_addr_cr = ((u32)iep_msg->dst.v_addr) + (offset_addr_v << 10);
1181
1182                 // former frame when processing deinterlace
1183                 dst_addr_y1 = ((u32)iep_msg->dst1.mem_addr) + (offset_addr_y << 10);
1184                 dst_addr_cbcr1 = ((u32)iep_msg->dst1.uv_addr) + (offset_addr_uv << 10);
1185                 dst_addr_cr1 = ((u32)iep_msg->dst1.v_addr) + (offset_addr_v << 10);
1186
1187                 dst_addr_y_itemp = ((u32)iep_msg->dst_itemp.mem_addr) +
1188                         (offset_addr_y << 10);
1189                 dst_addr_cbcr_itemp = ((u32)iep_msg->dst_itemp.uv_addr) +
1190                         (offset_addr_uv << 10);
1191                 dst_addr_cr_itemp = ((u32)iep_msg->dst_itemp.v_addr) +
1192                         (offset_addr_v << 10);
1193
1194                 dst_addr_y_ftemp = ((u32)iep_msg->dst_ftemp.mem_addr) +
1195                         (offset_addr_y << 10);
1196                 dst_addr_cbcr_ftemp = ((u32)iep_msg->dst_ftemp.uv_addr) +
1197                         (offset_addr_uv << 10);
1198                 dst_addr_cr_ftemp = ((u32)iep_msg->dst_ftemp.v_addr) +
1199                         (offset_addr_v << 10);
1200         }
1201
1202         IEP_REGB_DST_ADDR_YRGB(iep_msg->base, dst_addr_yrgb);
1203         IEP_REGB_DST_ADDR_CBCR(iep_msg->base, dst_addr_cbcr);
1204         IEP_REGB_DST_ADDR_Y1(iep_msg->base, dst_addr_y1);
1205         IEP_REGB_DST_ADDR_CBCR1(iep_msg->base, dst_addr_cbcr1);
1206         IEP_REGB_DST_ADDR_CR(iep_msg->base, dst_addr_cr);
1207         IEP_REGB_DST_ADDR_CR1(iep_msg->base, dst_addr_cr1);
1208
1209         if (iep_msg->yuv_3D_denoise_en) {
1210                 IEP_REGB_DST_ADDR_Y_ITEMP(iep_msg->base,
1211                         dst_addr_y_itemp);
1212                 IEP_REGB_DST_ADDR_CBCR_ITEMP(iep_msg->base,
1213                         dst_addr_cbcr_itemp);
1214                 IEP_REGB_DST_ADDR_Y_FTEMP(iep_msg->base,
1215                         dst_addr_y_ftemp);
1216                 IEP_REGB_DST_ADDR_CBCR_FTEMP(iep_msg->base,
1217                         dst_addr_cbcr_ftemp);
1218                 if ((iep_msg->dst.format == IEP_FORMAT_YCbCr_422_P) ||
1219                     (iep_msg->dst.format == IEP_FORMAT_YCbCr_420_P) ||
1220                     (iep_msg->dst.format == IEP_FORMAT_YCrCb_422_P) ||
1221                     (iep_msg->dst.format == IEP_FORMAT_YCrCb_420_P)) {
1222                         IEP_REGB_DST_ADDR_CR_ITEMP(iep_msg->base,
1223                                 dst_addr_cr_itemp);
1224                         IEP_REGB_DST_ADDR_CR_FTEMP(iep_msg->base,
1225                                 dst_addr_cr_ftemp);
1226                 }
1227         }
1228 #ifdef IEP_PRINT_INFO
1229         IEP_DBG("//-------destination address for image-------// \n\n");
1230         IEP_DBG("sw_dst_addr_yrgb           = 32'h%x;\n",
1231                 (u32)iep_msg->dst.mem_addr);
1232         IEP_DBG("sw_dst_addr_cbcr           = 32'h%x;\n",
1233                 (u32)iep_msg->dst.uv_addr);
1234         IEP_DBG("sw_dst_addr_cr             = 32'h%x;\n",
1235                 (u32)iep_msg->dst.v_addr);
1236         IEP_DBG("sw_dst_addr_y1             = 32'h%x;\n",
1237                 (u32)iep_msg->dst1.mem_addr);
1238         IEP_DBG("sw_dst_addr_cbcr0          = 32'h%x;\n",
1239                 (u32)iep_msg->dst1.uv_addr);
1240         IEP_DBG("sw_dst_addr_cr0            = 32'h%x;\n",
1241                 (u32)iep_msg->dst1.v_addr);
1242         IEP_DBG("sw_dst_addr_y_itemp        = 32'h%x;\n",
1243                 (u32)iep_msg->dst_itemp.mem_addr);
1244         IEP_DBG("sw_dst_addr_cbcr_itemp     = 32'h%x;\n",
1245                 (u32)iep_msg->dst_itemp.uv_addr);
1246         IEP_DBG("sw_dst_addr_cr_itemp       = 32'h%x;\n",
1247                 (u32)iep_msg->dst_itemp.v_addr);
1248         IEP_DBG("sw_dst_addr_y_ftemp        = 32'h%x;\n",
1249                 (u32)iep_msg->dst_ftemp.mem_addr);
1250         IEP_DBG("sw_dst_addr_cbcr_ftemp     = 32'h%x;\n",
1251                 (u32)iep_msg->dst_ftemp.uv_addr);
1252         IEP_DBG("sw_dst_addr_cr_ftemp       = 32'h%x;\n\n",
1253                 (u32)iep_msg->dst_ftemp.v_addr);
1254 #endif
1255 }
1256
1257 void iep_config_lcdc_path(struct IEP_MSG *iep_msg)
1258 {
1259         IEP_REGB_LCDC_PATH_EN(iep_msg->base, iep_msg->lcdc_path_en);
1260
1261 #ifdef IEP_PRINT_INFO
1262         IEP_DBG("//==write back or lcdc direct path config=====// \n\n");
1263         IEP_DBG("sw_lcdc_path_en = %d;//lcdc direct path enable,c"
1264                 " model don't care this value\n\n", iep_msg->lcdc_path_en);
1265 #endif
1266 }
1267
1268 int iep_probe_int(void *base)
1269 {
1270         return ReadReg32(base, rIEP_INT) & 1;
1271 }
1272
1273 void iep_config_frame_end_int_clr(void *base)
1274 {
1275         IEP_REGB_FRAME_END_INT_CLR(base, 1);
1276 }
1277
1278 void iep_config_frame_end_int_en(void *base)
1279 {
1280         IEP_REGB_FRAME_END_INT_CLR(base, 1);
1281         IEP_REGB_FRAME_END_INT_EN(base, 1);
1282 }
1283
1284 void iep_config_misc(struct IEP_MSG *iep_msg)
1285 {
1286 //      IEP_REGB_V_REVERSE_DISP();
1287 //      IEP_REGB_H_REVERSE_DISP();
1288 #ifdef IEP_PRINT_INFO
1289         IEP_DBG("//==misc config==========================//\n\n");
1290         IEP_DBG("sw_v_reverse_disp          = 0;\n");
1291         IEP_DBG("sw_u_reverse_disp          = 0;\n\n");
1292 #endif
1293 }
1294
1295 #define IEP_RESET_TIMEOUT   1000
1296 void iep_soft_rst(void *base)
1297 {
1298         unsigned int rst_state = 0;
1299         int i = 0;
1300         WriteReg32(base, rIEP_SOFT_RST, 2);
1301         WriteReg32(base, rIEP_SOFT_RST, 1);
1302         while (i++ < IEP_RESET_TIMEOUT) {
1303                 rst_state = ReadReg32(base, IEP_STATUS);
1304                 if ((rst_state & 0x200) == 0x200) {
1305                         break;
1306                 }
1307
1308                 udelay(1);
1309         }
1310         WriteReg32(base, IEP_SOFT_RST, 2);
1311
1312         if (i == IEP_RESET_TIMEOUT)
1313                 IEP_DBG("soft reset timeout.\n");
1314 }
1315
1316 void iep_config_done(void *base)
1317 {
1318         WriteReg32(base, rIEP_CONF_DONE, 1);
1319 }
1320
1321 void iep_config_frm_start(void *base)
1322 {
1323         IEP_REGB_FRM_START(base, 1);
1324 }
1325
1326 struct iep_status iep_get_status(void *base)
1327 {
1328         uint32_t sts_int = IEP_REGB_STATUS(base);
1329         struct iep_status sts;
1330
1331         memcpy(&sts, &sts_int, 4);
1332
1333         return sts;
1334 }
1335
1336 int iep_get_deinterlace_mode(void *base)
1337 {
1338         int cfg = ReadReg32(base, IEP_CONFIG0);
1339         return (cfg >> 8) & 0x7;
1340 }
1341
1342 void iep_set_deinterlace_mode(int mode, void *base)
1343 {
1344         int cfg;
1345
1346         if (mode > dein_mode_bypass) {
1347                 IEP_ERR("invalid deinterlace mode\n");
1348                 return;
1349         }
1350
1351         cfg = ReadReg32(base, RAW_IEP_CONFIG0);
1352         cfg = (cfg & (~(7 << 8))) | (mode << 8);
1353         WriteReg32(base, IEP_CONFIG0, cfg);
1354
1355         //IEP_REGB_DIL_MODE(base, mode);
1356 }
1357
1358 void iep_switch_input_address(void *base)
1359 {
1360         u32 src_addr_yrgb  = ReadReg32(base, IEP_SRC_ADDR_YRGB);
1361         u32 src_addr_cbcr  = ReadReg32(base, IEP_SRC_ADDR_CBCR);
1362         u32 src_addr_cr    = ReadReg32(base, IEP_SRC_ADDR_CR);
1363
1364         u32 src_addr_y1    = ReadReg32(base, IEP_SRC_ADDR_Y1);
1365         u32 src_addr_cbcr1 = ReadReg32(base, IEP_SRC_ADDR_CBCR1);
1366         u32 src_addr_cr1   = ReadReg32(base, IEP_SRC_ADDR_CR1);
1367
1368         IEP_REGB_SRC_ADDR_YRGB(base, src_addr_y1);
1369         IEP_REGB_SRC_ADDR_CBCR(base, src_addr_cbcr1);
1370         IEP_REGB_SRC_ADDR_CR(base, src_addr_cr1);
1371         IEP_REGB_SRC_ADDR_Y1(base, src_addr_yrgb);
1372         IEP_REGB_SRC_ADDR_CBCR1(base, src_addr_cbcr);
1373         IEP_REGB_SRC_ADDR_CR1(base, src_addr_cr);
1374 }
1375
1376 static int iep_bufid_to_iova(iep_service_info *pservice, u8 *tbl,
1377         int size, struct iep_reg *reg)
1378 {
1379         int i;
1380         int usr_fd = 0;
1381         int offset = 0;
1382
1383         if (tbl == NULL || size <= 0) {
1384                 dev_err(pservice->iommu_dev, "input arguments invalidate\n");
1385                 return -1;
1386         }
1387
1388         for (i = 0; i < size; i++) {
1389                 usr_fd = reg->reg[tbl[i]] & 0x3FF;
1390                 offset = reg->reg[tbl[i]] >> 10;
1391                 if (usr_fd != 0) {
1392                         int hdl;
1393                         int ret;
1394                         struct iep_mem_region *mem_region;
1395
1396                         hdl = iep_iommu_import(pservice->iommu_info,
1397                                                reg->session, usr_fd);
1398
1399                         mem_region = kzalloc(sizeof(struct iep_mem_region),
1400                                 GFP_KERNEL);
1401
1402                         if (mem_region == NULL) {
1403                                 dev_err(pservice->iommu_dev,
1404                                         "allocate memory for"
1405                                         " iommu memory region failed\n");
1406                                 iep_iommu_free(pservice->iommu_info,
1407                                                reg->session, hdl);
1408                                 return -ENOMEM;
1409                         }
1410
1411                         mem_region->hdl = hdl;
1412
1413                         ret = iep_iommu_map_iommu(pservice->iommu_info,
1414                                 reg->session, mem_region->hdl,
1415                                 &mem_region->iova, &mem_region->len);
1416                         if (ret < 0) {
1417                                 dev_err(pservice->iommu_dev,
1418                                         "ion map iommu failed\n");
1419                                 kfree(mem_region);
1420                                 iep_iommu_free(pservice->iommu_info,
1421                                                reg->session, hdl);
1422                                 return ret;
1423                         }
1424
1425                         reg->reg[tbl[i]] = mem_region->iova + offset;
1426                         INIT_LIST_HEAD(&mem_region->reg_lnk);
1427                         list_add_tail(&mem_region->reg_lnk,
1428                                 &reg->mem_region_list);
1429                 }
1430         }
1431
1432         return 0;
1433 }
1434
1435 static u8 addr_tbl_iep[] = {
1436         32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55
1437 };
1438
1439 static int iep_reg_address_translate(iep_service_info *pservice, struct iep_reg *reg)
1440 {
1441         return iep_bufid_to_iova(pservice, addr_tbl_iep, sizeof(addr_tbl_iep), reg);
1442 }
1443
1444 /**
1445  * generating a series of registers copy from iep message
1446  */
1447 void iep_config(iep_session *session, struct IEP_MSG *iep_msg)
1448 {
1449         struct iep_reg *reg = NULL;
1450         int w;
1451         int h;
1452
1453         reg = kzalloc(sizeof(*reg), GFP_KERNEL);
1454         if (!reg)
1455                 return;
1456         reg->session = session;
1457         iep_msg->base = reg->reg;
1458         atomic_set(&reg->session->done, 0);
1459
1460         INIT_LIST_HEAD(&reg->session_link);
1461         INIT_LIST_HEAD(&reg->status_link);
1462
1463         INIT_LIST_HEAD(&reg->mem_region_list);
1464
1465         //write config
1466         iep_config_src_size(iep_msg);
1467         iep_config_dst_size(iep_msg);
1468         iep_config_dst_width_tile(iep_msg); //not implement
1469         iep_config_dst_fmt(iep_msg);
1470         iep_config_src_fmt(iep_msg);
1471         iep_config_scl(iep_msg);
1472         iep_config_cg_order(iep_msg);
1473
1474         iep_config_cg(iep_msg);
1475         iep_config_dde(iep_msg);            //not implement
1476         iep_config_color_enh(iep_msg);      //not implement
1477         iep_config_yuv_dns(iep_msg);
1478         iep_config_dil(iep_msg);
1479         iep_config_yuv_enh(iep_msg);
1480         iep_config_rgb2yuv(iep_msg);
1481         iep_config_yuv2rgb(iep_msg);
1482         iep_config_dither_up(iep_msg);
1483         iep_config_dither_down(iep_msg);
1484         iep_config_glb_alpha(iep_msg);
1485         iep_config_vir_line(iep_msg);
1486         iep_config_src_addr(iep_msg);
1487         iep_config_dst_addr(iep_msg);
1488         iep_config_lcdc_path(iep_msg);
1489         iep_config_misc(iep_msg);           //not implement
1490
1491         if (iep_msg->lcdc_path_en) {
1492                 reg->dpi_en     = true;
1493                 reg->act_width  = iep_msg->dst.act_w;
1494                 reg->act_height = iep_msg->dst.act_h;
1495                 reg->off_x      = iep_msg->off_x;
1496                 reg->off_y      = iep_msg->off_y;
1497                 reg->vir_width  = iep_msg->width;
1498                 reg->vir_height = iep_msg->height;
1499                 reg->layer      = iep_msg->layer;
1500                 reg->format     = iep_msg->dst.format;
1501         } else {
1502                 reg->dpi_en     = false;
1503         }
1504
1505         if (iep_service.iommu_dev) {
1506                 if (0 > iep_reg_address_translate(&iep_service, reg)) {
1507                         IEP_ERR("error: translate reg address failed\n");
1508                         kfree(reg);
1509                         return;
1510                 }
1511         }
1512
1513         /* workaround for iommu enable case when 4k video input */
1514         w = (iep_msg->src.act_w + 15) & (0xfffffff0);
1515         h = (iep_msg->src.act_h + 15) & (0xfffffff0);
1516         if (w > 1920 && iep_msg->src.format == IEP_FORMAT_YCbCr_420_SP)
1517                 reg->reg[33] = reg->reg[32] + w * h;
1518
1519         w = (iep_msg->dst.act_w + 15) & (0xfffffff0);
1520         h = (iep_msg->dst.act_h + 15) & (0xfffffff0);
1521         if (w > 1920 && iep_msg->dst.format == IEP_FORMAT_YCbCr_420_SP)
1522                 reg->reg[45] = reg->reg[44] + w * h;
1523
1524         mutex_lock(&iep_service.lock);
1525
1526         list_add_tail(&reg->status_link, &iep_service.waiting);
1527         list_add_tail(&reg->session_link, &session->waiting);
1528         mutex_unlock(&iep_service.lock);
1529 }
1530