video/rockchip: rga2: fix compilation warning
[firefly-linux-kernel-4.4.55.git] / drivers / video / rockchip / rga2 / rga2_mmu_info.c
1 \r
2 \r
3 #include <linux/version.h>\r
4 #include <linux/init.h>\r
5 #include <linux/module.h>\r
6 #include <linux/fs.h>\r
7 #include <linux/sched.h>\r
8 #include <linux/signal.h>\r
9 #include <linux/pagemap.h>\r
10 #include <linux/seq_file.h>\r
11 #include <linux/mm.h>\r
12 #include <linux/mman.h>\r
13 #include <linux/sched.h>\r
14 #include <linux/slab.h>\r
15 #include <linux/memory.h>\r
16 #include <linux/dma-mapping.h>\r
17 #include <linux/scatterlist.h>\r
18 #include <asm/memory.h>\r
19 #include <asm/atomic.h>\r
20 #include <asm/cacheflush.h>\r
21 #include "rga2_mmu_info.h"\r
22 \r
23 extern struct rga2_service_info rga2_service;\r
24 extern struct rga2_mmu_buf_t rga2_mmu_buf;\r
25 \r
26 //extern int mmu_buff_temp[1024];\r
27 \r
28 #define KERNEL_SPACE_VALID    0xc0000000\r
29 \r
30 #define V7_VATOPA_SUCESS_MASK   (0x1)\r
31 #define V7_VATOPA_GET_PADDR(X)  (X & 0xFFFFF000)\r
32 #define V7_VATOPA_GET_INER(X)           ((X>>4) & 7)\r
33 #define V7_VATOPA_GET_OUTER(X)          ((X>>2) & 3)\r
34 #define V7_VATOPA_GET_SH(X)             ((X>>7) & 1)\r
35 #define V7_VATOPA_GET_NS(X)             ((X>>9) & 1)\r
36 #define V7_VATOPA_GET_SS(X)             ((X>>1) & 1)\r
37 \r
38 static void rga_dma_flush_range(void *pstart, void *pend)
39 {
40 #ifdef CONFIG_ARM
41         dmac_flush_range(pstart, pend);
42         outer_flush_range(virt_to_phys(pstart), virt_to_phys(pend));
43 #elif defined(CONFIG_ARM64)
44         __dma_flush_range(pstart, pend);
45 #endif
46 }
47
48 #if 0\r
49 static unsigned int armv7_va_to_pa(unsigned int v_addr)\r
50 {\r
51         unsigned int p_addr;\r
52         __asm__ volatile (      "mcr p15, 0, %1, c7, c8, 0\n"\r
53                                                 "isb\n"\r
54                                                 "dsb\n"\r
55                                                 "mrc p15, 0, %0, c7, c4, 0\n"\r
56                                                 : "=r" (p_addr)\r
57                                                 : "r" (v_addr)\r
58                                                 : "cc");\r
59 \r
60         if (p_addr & V7_VATOPA_SUCESS_MASK)\r
61                 return 0xFFFFFFFF;\r
62         else\r
63                 return (V7_VATOPA_GET_SS(p_addr) ? 0xFFFFFFFF : V7_VATOPA_GET_PADDR(p_addr));\r
64 }\r
65 #endif\r
66 \r
67 static int rga2_mmu_buf_get(struct rga2_mmu_buf_t *t, uint32_t size)\r
68 {\r
69     mutex_lock(&rga2_service.lock);\r
70     t->front += size;\r
71     mutex_unlock(&rga2_service.lock);\r
72 \r
73     return 0;\r
74 }\r
75 \r
76 static int rga2_mmu_buf_get_try(struct rga2_mmu_buf_t *t, uint32_t size)
77 {
78         int ret = 0;
79
80         mutex_lock(&rga2_service.lock);
81         if ((t->back - t->front) > t->size) {
82                 if (t->front + size > t->back - t->size) {
83                         pr_info("front %d, back %d dsize %d size %d",
84                                 t->front, t->back, t->size, size);
85                         ret = -ENOMEM;
86                         goto out;
87                 }
88         } else {
89                 if ((t->front + size) > t->back) {
90                         pr_info("front %d, back %d dsize %d size %d",
91                                 t->front, t->back, t->size, size);
92                         ret = -ENOMEM;
93                         goto out;
94                 }
95
96                 if (t->front + size > t->size) {
97                         if (size > (t->back - t->size)) {
98                                 pr_info("front %d, back %d dsize %d size %d",
99                                         t->front, t->back, t->size, size);
100                                 ret = -ENOMEM;
101                                 goto out;
102                         }
103                         t->front = 0;
104                 }
105         }
106 out:
107         mutex_unlock(&rga2_service.lock);
108         return ret;
109 }
110
111 static int rga2_mem_size_cal(unsigned long Mem, uint32_t MemSize, unsigned long *StartAddr)\r
112 {\r
113     unsigned long start, end;\r
114     uint32_t pageCount;\r
115 \r
116     end = (Mem + (MemSize + PAGE_SIZE - 1)) >> PAGE_SHIFT;\r
117     start = Mem >> PAGE_SHIFT;\r
118     pageCount = end - start;\r
119     *StartAddr = start;\r
120     return pageCount;\r
121 }\r
122 \r
123 static int rga2_buf_size_cal(unsigned long yrgb_addr, unsigned long uv_addr, unsigned long v_addr,\r
124                                         int format, uint32_t w, uint32_t h, unsigned long *StartAddr )\r
125 {\r
126     uint32_t size_yrgb = 0;\r
127     uint32_t size_uv = 0;\r
128     uint32_t size_v = 0;\r
129     uint32_t stride = 0;\r
130     unsigned long start, end;\r
131     uint32_t pageCount;\r
132 \r
133     switch(format)\r
134     {\r
135         case RGA2_FORMAT_RGBA_8888 :\r
136             stride = (w * 4 + 3) & (~3);\r
137             size_yrgb = stride*h;\r
138             start = yrgb_addr >> PAGE_SHIFT;\r
139             pageCount = (size_yrgb + PAGE_SIZE - 1) >> PAGE_SHIFT;\r
140             break;\r
141         case RGA2_FORMAT_RGBX_8888 :\r
142             stride = (w * 4 + 3) & (~3);\r
143             size_yrgb = stride*h;\r
144             start = yrgb_addr >> PAGE_SHIFT;\r
145             pageCount = (size_yrgb + PAGE_SIZE - 1) >> PAGE_SHIFT;\r
146             break;\r
147         case RGA2_FORMAT_RGB_888 :\r
148             stride = (w * 3 + 3) & (~3);\r
149             size_yrgb = stride*h;\r
150             start = yrgb_addr >> PAGE_SHIFT;\r
151             pageCount = (size_yrgb + PAGE_SIZE - 1) >> PAGE_SHIFT;\r
152             break;\r
153         case RGA2_FORMAT_BGRA_8888 :\r
154             size_yrgb = w*h*4;\r
155             start = yrgb_addr >> PAGE_SHIFT;\r
156             pageCount = (size_yrgb + PAGE_SIZE - 1) >> PAGE_SHIFT;\r
157             break;\r
158         case RGA2_FORMAT_RGB_565 :\r
159             stride = (w*2 + 3) & (~3);\r
160             size_yrgb = stride * h;\r
161             start = yrgb_addr >> PAGE_SHIFT;\r
162             pageCount = (size_yrgb + PAGE_SIZE - 1) >> PAGE_SHIFT;\r
163             break;\r
164         case RGA2_FORMAT_RGBA_5551 :\r
165             stride = (w*2 + 3) & (~3);\r
166             size_yrgb = stride * h;\r
167             start = yrgb_addr >> PAGE_SHIFT;\r
168             pageCount = (size_yrgb + PAGE_SIZE - 1) >> PAGE_SHIFT;\r
169             break;\r
170         case RGA2_FORMAT_RGBA_4444 :\r
171             stride = (w*2 + 3) & (~3);\r
172             size_yrgb = stride * h;\r
173             start = yrgb_addr >> PAGE_SHIFT;\r
174             pageCount = (size_yrgb + PAGE_SIZE - 1) >> PAGE_SHIFT;\r
175             break;\r
176         case RGA2_FORMAT_BGR_888 :\r
177             stride = (w*3 + 3) & (~3);\r
178             size_yrgb = stride * h;\r
179             start = yrgb_addr >> PAGE_SHIFT;\r
180             pageCount = (size_yrgb + PAGE_SIZE - 1) >> PAGE_SHIFT;\r
181             break;\r
182 \r
183         /* YUV FORMAT */\r
184         case RGA2_FORMAT_YCbCr_422_SP :\r
185         case RGA2_FORMAT_YCrCb_422_SP :\r
186             stride = (w + 3) & (~3);\r
187             size_yrgb = stride * h;\r
188             size_uv = stride * h;\r
189             start = MIN(yrgb_addr, uv_addr);\r
190             start >>= PAGE_SHIFT;\r
191             end = MAX((yrgb_addr + size_yrgb), (uv_addr + size_uv));\r
192             end = (end + (PAGE_SIZE - 1)) >> PAGE_SHIFT;\r
193             pageCount = end - start;\r
194             break;\r
195         case RGA2_FORMAT_YCbCr_422_P :\r
196         case RGA2_FORMAT_YCrCb_422_P :\r
197             stride = (w + 3) & (~3);\r
198             size_yrgb = stride * h;\r
199             size_uv = ((stride >> 1) * h);\r
200             size_v = ((stride >> 1) * h);\r
201             start = MIN(MIN(yrgb_addr, uv_addr), v_addr);\r
202             start = start >> PAGE_SHIFT;\r
203             end = MAX(MAX((yrgb_addr + size_yrgb), (uv_addr + size_uv)), (v_addr + size_v));\r
204             end = (end + (PAGE_SIZE - 1)) >> PAGE_SHIFT;\r
205             pageCount = end - start;\r
206             break;\r
207         case RGA2_FORMAT_YCbCr_420_SP :\r
208         case RGA2_FORMAT_YCrCb_420_SP :\r
209             stride = (w + 3) & (~3);\r
210             size_yrgb = stride * h;\r
211             size_uv = (stride * (h >> 1));\r
212             start = MIN(yrgb_addr, uv_addr);\r
213             start >>= PAGE_SHIFT;\r
214             end = MAX((yrgb_addr + size_yrgb), (uv_addr + size_uv));\r
215             end = (end + (PAGE_SIZE - 1)) >> PAGE_SHIFT;\r
216             pageCount = end - start;\r
217             break;\r
218         case RGA2_FORMAT_YCbCr_420_P :\r
219         case RGA2_FORMAT_YCrCb_420_P :\r
220             stride = (w + 3) & (~3);\r
221             size_yrgb = stride * h;\r
222             size_uv = ((stride >> 1) * (h >> 1));\r
223             size_v = ((stride >> 1) * (h >> 1));\r
224             start = MIN(MIN(yrgb_addr, uv_addr), v_addr);\r
225             start >>= PAGE_SHIFT;\r
226             end = MAX(MAX((yrgb_addr + size_yrgb), (uv_addr + size_uv)), (v_addr + size_v));\r
227             end = (end + (PAGE_SIZE - 1)) >> PAGE_SHIFT;\r
228             pageCount = end - start;\r
229             break;\r
230         #if 0\r
231         case RK_FORMAT_BPP1 :\r
232             break;\r
233         case RK_FORMAT_BPP2 :\r
234             break;\r
235         case RK_FORMAT_BPP4 :\r
236             break;\r
237         case RK_FORMAT_BPP8 :\r
238             break;\r
239         #endif\r
240         case RGA2_FORMAT_YCbCr_420_SP_10B:\r
241         case RGA2_FORMAT_YCrCb_420_SP_10B:\r
242             stride = (w + 3) & (~3);\r
243             stride = stride;\r
244             size_yrgb = stride * h;\r
245             size_uv = (stride * (h >> 1));\r
246             start = MIN(yrgb_addr, uv_addr);\r
247             start >>= PAGE_SHIFT;\r
248             end = MAX((yrgb_addr + size_yrgb), (uv_addr + size_uv));\r
249             end = (end + (PAGE_SIZE - 1)) >> PAGE_SHIFT;\r
250             pageCount = end - start;\r
251             break;\r
252         default :\r
253             pageCount = 0;\r
254             start = 0;\r
255             break;\r
256     }\r
257 \r
258     *StartAddr = start;\r
259     return pageCount;\r
260 }\r
261 \r
262 static int rga2_MapUserMemory(struct page **pages, uint32_t *pageTable,
263                               unsigned long Memory, uint32_t pageCount,
264                               int writeFlag)
265 {
266         struct vm_area_struct *vma;
267         int32_t result;
268         uint32_t i;
269         uint32_t status;
270         unsigned long Address;
271         unsigned long pfn;
272         void *virt;
273         spinlock_t * ptl;
274         pte_t * pte;
275         pgd_t * pgd;
276         pud_t * pud;
277         pmd_t * pmd;
278
279         status = 0;
280         Address = 0;
281         down_read(&current->mm->mmap_sem);
282 #if LINUX_VERSION_CODE < KERNEL_VERSION(4, 6, 0)
283         result = get_user_pages(current, current->mm, Memory << PAGE_SHIFT,
284                                 pageCount, writeFlag, 0, pages, NULL);
285 #else
286         result = get_user_pages_remote(current, current->mm,
287                                        Memory << PAGE_SHIFT,
288                                        pageCount, writeFlag, 0, pages, NULL);
289 #endif
290         if (result > 0 && result >= pageCount) {
291                 /* Fill the page table. */
292                 for (i = 0; i < pageCount; i++) {
293                         /* Get the physical address from page struct. */
294                         pageTable[i] = page_to_phys(pages[i]);
295                         virt = phys_to_virt(pageTable[i]);
296                         rga_dma_flush_range(virt, virt + 4 * 1024);
297                 }
298                 for (i = 0; i < result; i++)
299                         put_page(pages[i]);
300                 up_read(&current->mm->mmap_sem);
301                 return 0;
302         }
303         if (result > 0) {
304                 for (i = 0; i < result; i++)
305                         put_page(pages[i]);
306         }
307         for (i = 0; i < pageCount; i++) {
308                 vma = find_vma(current->mm, (Memory + i) << PAGE_SHIFT);
309                 if (!vma) {
310                         status = RGA2_OUT_OF_RESOURCES;
311                         break;
312                 }
313                 pgd = pgd_offset(current->mm, (Memory + i) << PAGE_SHIFT);
314                 if (pgd_val(*pgd) == 0) {
315                         status = RGA2_OUT_OF_RESOURCES;
316                         break;
317                 }
318                 pud = pud_offset(pgd, (Memory + i) << PAGE_SHIFT);
319                 if (!pud) {
320                         status = RGA2_OUT_OF_RESOURCES;
321                         break;
322                 }
323                 pmd = pmd_offset(pud, (Memory + i) << PAGE_SHIFT);
324                 if (!pmd) {
325                         status = RGA2_OUT_OF_RESOURCES;
326                         break;
327                 }
328                 pte = pte_offset_map_lock(current->mm, pmd,
329                                           (Memory + i) << PAGE_SHIFT,
330                                           &ptl);
331                 if (!pte) {
332                         pte_unmap_unlock(pte, ptl);
333                         status = RGA2_OUT_OF_RESOURCES;
334                         break;
335                 }
336                 pfn = pte_pfn(*pte);
337                 Address = ((pfn << PAGE_SHIFT) | (((unsigned long)((Memory + i)
338                            << PAGE_SHIFT)) & ~PAGE_MASK));
339                 pte_unmap_unlock(pte, ptl);
340                 pageTable[i] = (uint32_t)Address;
341                 virt = phys_to_virt(pageTable[i]);
342                 rga_dma_flush_range(virt, virt + 4 * 1024);
343         }
344         up_read(&current->mm->mmap_sem);
345         return status;
346 }
347
348 static int rga2_MapION(struct sg_table *sg,\r
349                                uint32_t *Memory,\r
350                                int32_t  pageCount)\r
351 {\r
352     uint32_t i;\r
353     uint32_t status;\r
354     unsigned long Address;\r
355     uint32_t mapped_size = 0;\r
356     uint32_t len;\r
357     struct scatterlist *sgl = sg->sgl;\r
358     uint32_t sg_num = 0;\r
359     uint32_t break_flag = 0;\r
360 \r
361     status = 0;\r
362     Address = 0;\r
363     do {\r
364         len = sg_dma_len(sgl) >> PAGE_SHIFT;\r
365         Address = sg_phys(sgl);\r
366 \r
367         for(i=0; i<len; i++) {\r
368             if (mapped_size + i >= pageCount) {\r
369                 break_flag = 1;\r
370                 break;\r
371             }\r
372             Memory[mapped_size + i] = (uint32_t)(Address + (i << PAGE_SHIFT));\r
373         }\r
374         if (break_flag)\r
375             break;\r
376         mapped_size += len;\r
377         sg_num += 1;\r
378     }\r
379     while((sgl = sg_next(sgl)) && (mapped_size < pageCount) && (sg_num < sg->nents));\r
380 \r
381     return 0;\r
382 }\r
383 \r
384 \r
385 static int rga2_mmu_info_BitBlt_mode(struct rga2_reg *reg, struct rga2_req *req)
386 {
387         int Src0MemSize, DstMemSize, Src1MemSize;
388         unsigned long Src0Start, Src1Start, DstStart;
389         unsigned long Src0PageCount, Src1PageCount, DstPageCount;
390         uint32_t AllSize;
391         uint32_t *MMU_Base, *MMU_Base_phys;
392         int ret;
393         int status;
394         uint32_t uv_size, v_size;
395         struct page **pages = NULL;
396         MMU_Base = NULL;
397         Src0MemSize = 0;
398         Src1MemSize = 0;
399         DstMemSize  = 0;
400         Src0PageCount = 0;
401         Src1PageCount = 0;
402         DstPageCount = 0;
403
404         /* cal src0 buf mmu info */
405         if (req->mmu_info.src0_mmu_flag & 1) {
406                 Src0PageCount = rga2_buf_size_cal(req->src.yrgb_addr,
407                                                   req->src.uv_addr,
408                                                   req->src.v_addr,
409                                                   req->src.format,
410                                                   req->src.vir_w,
411                                                   (req->src.vir_h),
412                                                   &Src0Start);
413                 if (Src0PageCount == 0)
414                         return -EINVAL;
415         }
416         /* cal src1 buf mmu info */
417         if (req->mmu_info.src1_mmu_flag & 1) {
418                 Src1PageCount = rga2_buf_size_cal(req->src1.yrgb_addr,
419                                                   req->src1.uv_addr,
420                                                   req->src1.v_addr,
421                                                   req->src1.format,
422                                                   req->src1.vir_w,
423                                                   (req->src1.vir_h),
424                                                   &Src1Start);
425                 Src1PageCount = (Src1PageCount + 3) & (~3);
426                 if (Src1PageCount == 0)
427                         return -EINVAL;
428         }
429         /* cal dst buf mmu info */
430         if (req->mmu_info.dst_mmu_flag & 1) {
431                 DstPageCount = rga2_buf_size_cal(req->dst.yrgb_addr,
432                                                  req->dst.uv_addr,
433                                                  req->dst.v_addr,
434                                                  req->dst.format,
435                                                  req->dst.vir_w,
436                                                  req->dst.vir_h,
437                                                  &DstStart);
438                 if (DstPageCount == 0)
439                         return -EINVAL;
440         }
441         /* Cal out the needed mem size */
442         Src0MemSize = (Src0PageCount + 15) & (~15);
443         Src1MemSize = (Src1PageCount + 15) & (~15);
444         DstMemSize  = (DstPageCount + 15) & (~15);
445         AllSize = Src0MemSize + Src1MemSize + DstMemSize;
446
447         if (rga2_mmu_buf_get_try(&rga2_mmu_buf, AllSize)) {
448                 pr_err("RGA2 Get MMU mem failed\n");
449                 status = RGA2_MALLOC_ERROR;
450                 goto out;
451         }
452         pages = rga2_mmu_buf.pages;
453         mutex_lock(&rga2_service.lock);
454         MMU_Base = rga2_mmu_buf.buf_virtual +
455                                 (rga2_mmu_buf.front & (rga2_mmu_buf.size - 1));
456         MMU_Base_phys = rga2_mmu_buf.buf +
457                                 (rga2_mmu_buf.front & (rga2_mmu_buf.size - 1));
458         mutex_unlock(&rga2_service.lock);
459         if (Src0MemSize) {
460                 if (req->sg_src0)
461                         ret = rga2_MapION(req->sg_src0,
462                                           &MMU_Base[0], Src0MemSize);
463                 else
464                         ret = rga2_MapUserMemory(&pages[0], &MMU_Base[0],
465                                                  Src0Start, Src0PageCount, 0);
466
467                 if (ret < 0) {
468                         pr_err("rga2 map src0 memory failed\n");
469                         status = ret;
470                         goto out;
471                 }
472                 /* change the buf address in req struct */
473                 req->mmu_info.src0_base_addr = (((unsigned long)MMU_Base_phys));
474                 uv_size = (req->src.uv_addr
475                            - (Src0Start << PAGE_SHIFT)) >> PAGE_SHIFT;
476                 v_size = (req->src.v_addr
477                           - (Src0Start << PAGE_SHIFT)) >> PAGE_SHIFT;
478
479                 req->src.yrgb_addr = (req->src.yrgb_addr & (~PAGE_MASK));
480                 req->src.uv_addr = (req->src.uv_addr & (~PAGE_MASK)) |
481                                                         (uv_size << PAGE_SHIFT);
482                 req->src.v_addr = (req->src.v_addr & (~PAGE_MASK)) |
483                                                         (v_size << PAGE_SHIFT);
484         }
485         if (Src1MemSize) {
486                 if (req->sg_src1)
487                         ret = rga2_MapION(req->sg_src1,
488                                         MMU_Base + Src0MemSize, Src1MemSize);
489                 else
490                         ret = rga2_MapUserMemory(&pages[0],
491                                                  MMU_Base + Src0MemSize,
492                                                  Src1Start, Src1PageCount, 0);
493                 if (ret < 0) {
494                         pr_err("rga2 map src1 memory failed\n");
495                         status = ret;
496                         goto out;
497                 }
498                 /* change the buf address in req struct */
499                 req->mmu_info.src1_base_addr = ((unsigned long)(MMU_Base_phys
500                                                 + Src0MemSize));
501                 req->src1.yrgb_addr = (req->src.yrgb_addr & (~PAGE_MASK));
502         }
503         if (DstMemSize) {
504                 if (req->sg_dst)
505                         ret = rga2_MapION(req->sg_dst, MMU_Base + Src0MemSize
506                                           + Src1MemSize, DstMemSize);
507                 else
508                         ret = rga2_MapUserMemory(&pages[0], MMU_Base
509                                                  + Src0MemSize + Src1MemSize,
510                                                  DstStart, DstPageCount, 1);
511                 if (ret < 0) {
512                         pr_err("rga2 map dst memory failed\n");
513                         status = ret;
514                         goto out;
515                 }
516                 /* change the buf address in req struct */
517                 req->mmu_info.dst_base_addr  = ((unsigned long)(MMU_Base_phys
518                                         + Src0MemSize + Src1MemSize));
519                 req->dst.yrgb_addr = (req->dst.yrgb_addr & (~PAGE_MASK));
520                 uv_size = (req->dst.uv_addr
521                            - (DstStart << PAGE_SHIFT)) >> PAGE_SHIFT;
522                 v_size = (req->dst.v_addr
523                           - (DstStart << PAGE_SHIFT)) >> PAGE_SHIFT;
524                 req->dst.uv_addr = (req->dst.uv_addr & (~PAGE_MASK)) |
525                                                    ((uv_size) << PAGE_SHIFT);
526                 req->dst.v_addr = (req->dst.v_addr & (~PAGE_MASK)) |
527                         ((v_size) << PAGE_SHIFT);
528
529                 if (((req->alpha_rop_flag & 1) == 1) && (req->bitblt_mode == 0)) {
530                         req->mmu_info.src1_base_addr = req->mmu_info.dst_base_addr;
531                         req->mmu_info.src1_mmu_flag  = req->mmu_info.dst_mmu_flag;
532                 }
533         }
534         /* flush data to DDR */
535         rga_dma_flush_range(MMU_Base, (MMU_Base + AllSize));
536         rga2_mmu_buf_get(&rga2_mmu_buf, AllSize);
537         reg->MMU_len = AllSize;
538         status = 0;
539 out:
540         return status;
541 }
542
543 static int rga2_mmu_info_color_palette_mode(struct rga2_reg *reg, struct rga2_req *req)\r
544 {\r
545     int SrcMemSize, DstMemSize;\r
546     unsigned long SrcStart, DstStart;\r
547     struct page **pages = NULL;\r
548     uint32_t AllSize;\r
549     uint32_t *MMU_Base = NULL, *MMU_Base_phys;\r
550     int ret, status;\r
551     uint32_t stride;\r
552 \r
553     uint8_t shift;\r
554     uint16_t sw, byte_num;\r
555 \r
556     shift = 3 - (req->palette_mode & 3);\r
557     sw = req->src.vir_w*req->src.vir_h;\r
558     byte_num = sw >> shift;\r
559     stride = (byte_num + 3) & (~3);\r
560 \r
561     SrcStart = 0;
562     DstStart = 0;
563     SrcMemSize = 0;\r
564     DstMemSize = 0;\r
565 \r
566     do {\r
567         if (req->mmu_info.src0_mmu_flag) {\r
568             SrcMemSize = rga2_mem_size_cal(req->src.yrgb_addr, stride, &SrcStart);\r
569             if(SrcMemSize == 0) {\r
570                 return -EINVAL;\r
571             }\r
572         }\r
573 \r
574         if (req->mmu_info.dst_mmu_flag) {\r
575             DstMemSize = rga2_buf_size_cal(req->dst.yrgb_addr, req->dst.uv_addr, req->dst.v_addr,\r
576                                             req->dst.format, req->dst.vir_w, req->dst.vir_h,\r
577                                             &DstStart);\r
578             if(DstMemSize == 0) {\r
579                 return -EINVAL;\r
580             }\r
581         }\r
582 \r
583         SrcMemSize = (SrcMemSize + 15) & (~15);\r
584         DstMemSize = (DstMemSize + 15) & (~15);\r
585 \r
586         AllSize = SrcMemSize + DstMemSize;\r
587 \r
588         if (rga2_mmu_buf_get_try(&rga2_mmu_buf, AllSize)) {\r
589             pr_err("RGA2 Get MMU mem failed\n");\r
590             status = RGA2_MALLOC_ERROR;\r
591             break;\r
592         }\r
593 \r
594         pages = rga2_mmu_buf.pages;\r
595         if(pages == NULL) {\r
596             pr_err("RGA MMU malloc pages mem failed\n");\r
597             return -EINVAL;\r
598         }\r
599 \r
600         mutex_lock(&rga2_service.lock);\r
601         MMU_Base = rga2_mmu_buf.buf_virtual + (rga2_mmu_buf.front & (rga2_mmu_buf.size - 1));\r
602         MMU_Base_phys = rga2_mmu_buf.buf + (rga2_mmu_buf.front & (rga2_mmu_buf.size - 1));\r
603         mutex_unlock(&rga2_service.lock);\r
604 \r
605         if(SrcMemSize) {\r
606                 ret = rga2_MapUserMemory(&pages[0], &MMU_Base[0],
607                                          SrcStart, SrcMemSize, 0);
608             if (ret < 0) {\r
609                 pr_err("rga2 map src0 memory failed\n");\r
610                 status = ret;\r
611                 break;\r
612             }\r
613 \r
614             /* change the buf address in req struct */\r
615             req->mmu_info.src0_base_addr = (((unsigned long)MMU_Base_phys));\r
616             req->src.yrgb_addr = (req->src.yrgb_addr & (~PAGE_MASK));\r
617         }\r
618 \r
619         if(DstMemSize) {\r
620                 ret = rga2_MapUserMemory(&pages[0], MMU_Base + SrcMemSize,
621                                          DstStart, DstMemSize, 1);
622             if (ret < 0) {\r
623                 pr_err("rga2 map dst memory failed\n");\r
624                 status = ret;\r
625                 break;\r
626             }\r
627 \r
628             /* change the buf address in req struct */\r
629             req->mmu_info.dst_base_addr  = ((unsigned long)(MMU_Base_phys + SrcMemSize));\r
630             req->dst.yrgb_addr = (req->dst.yrgb_addr & (~PAGE_MASK));\r
631         }\r
632 \r
633         /* flush data to DDR */\r
634         rga_dma_flush_range(MMU_Base, (MMU_Base + AllSize));
635         rga2_mmu_buf_get(&rga2_mmu_buf, AllSize);\r
636         reg->MMU_len = AllSize;\r
637 \r
638         return 0;\r
639     }\r
640     while(0);\r
641 \r
642     return 0;\r
643 }\r
644 \r
645 static int rga2_mmu_info_color_fill_mode(struct rga2_reg *reg, struct rga2_req *req)\r
646 {\r
647     int DstMemSize;\r
648     unsigned long DstStart;\r
649     struct page **pages = NULL;\r
650     uint32_t AllSize;\r
651     uint32_t *MMU_Base, *MMU_Base_phys;\r
652     int ret;\r
653     int status;\r
654 \r
655     DstMemSize = 0;
656     MMU_Base = NULL;\r
657 \r
658     do {\r
659         if(req->mmu_info.dst_mmu_flag & 1) {\r
660             DstMemSize = rga2_buf_size_cal(req->dst.yrgb_addr, req->dst.uv_addr, req->dst.v_addr,\r
661                                         req->dst.format, req->dst.vir_w, req->dst.vir_h,\r
662                                         &DstStart);\r
663             if(DstMemSize == 0) {\r
664                 return -EINVAL;\r
665             }\r
666         }\r
667 \r
668         AllSize = (DstMemSize + 15) & (~15);\r
669 \r
670         pages = rga2_mmu_buf.pages;\r
671 \r
672         if(rga2_mmu_buf_get_try(&rga2_mmu_buf, AllSize)) {\r
673            pr_err("RGA2 Get MMU mem failed\n");\r
674            status = RGA2_MALLOC_ERROR;\r
675            break;\r
676         }\r
677 \r
678         mutex_lock(&rga2_service.lock);\r
679         MMU_Base_phys = rga2_mmu_buf.buf + (rga2_mmu_buf.front & (rga2_mmu_buf.size - 1));\r
680         MMU_Base = rga2_mmu_buf.buf_virtual + (rga2_mmu_buf.front & (rga2_mmu_buf.size - 1));\r
681         mutex_unlock(&rga2_service.lock);\r
682 \r
683         if (DstMemSize) {\r
684             if (req->sg_dst) {\r
685                 ret = rga2_MapION(req->sg_dst, &MMU_Base[0], DstMemSize);\r
686             }\r
687             else {\r
688                     ret = rga2_MapUserMemory(&pages[0], &MMU_Base[0],
689                                              DstStart, DstMemSize, 1);
690             }\r
691             if (ret < 0) {\r
692                 pr_err("rga2 map dst memory failed\n");\r
693                 status = ret;\r
694                 break;\r
695             }\r
696 \r
697             /* change the buf address in req struct */\r
698             req->mmu_info.dst_base_addr = ((unsigned long)MMU_Base_phys);\r
699             req->dst.yrgb_addr = (req->dst.yrgb_addr & (~PAGE_MASK));\r
700         }\r
701 \r
702         /* flush data to DDR */\r
703         rga_dma_flush_range(MMU_Base, (MMU_Base + AllSize + 1));
704         rga2_mmu_buf_get(&rga2_mmu_buf, AllSize);\r
705 \r
706         return 0;\r
707     }\r
708     while(0);\r
709 \r
710     return status;\r
711 }\r
712 \r
713 \r
714 static int rga2_mmu_info_update_palette_table_mode(struct rga2_reg *reg, struct rga2_req *req)\r
715 {\r
716     int SrcMemSize;\r
717     unsigned long SrcStart;\r
718     struct page **pages = NULL;\r
719     uint32_t AllSize;\r
720     uint32_t *MMU_Base, *MMU_Base_phys;\r
721     int ret, status;\r
722 \r
723     MMU_Base = NULL;\r
724 \r
725     do {\r
726         /* cal src buf mmu info */\r
727         SrcMemSize = rga2_mem_size_cal(req->pat.yrgb_addr, req->pat.vir_w * req->pat.vir_h, &SrcStart);\r
728         if(SrcMemSize == 0) {\r
729             return -EINVAL;\r
730         }\r
731 \r
732         SrcMemSize = (SrcMemSize + 15) & (~15);\r
733         AllSize = SrcMemSize;\r
734 \r
735         if (rga2_mmu_buf_get_try(&rga2_mmu_buf, AllSize)) {\r
736             pr_err("RGA2 Get MMU mem failed\n");\r
737             status = RGA2_MALLOC_ERROR;\r
738             break;\r
739         }\r
740 \r
741         mutex_lock(&rga2_service.lock);\r
742         MMU_Base = rga2_mmu_buf.buf_virtual + (rga2_mmu_buf.front & (rga2_mmu_buf.size - 1));\r
743         MMU_Base_phys = rga2_mmu_buf.buf + (rga2_mmu_buf.front & (rga2_mmu_buf.size - 1));\r
744         mutex_unlock(&rga2_service.lock);\r
745 \r
746         pages = kzalloc(AllSize * sizeof(struct page *), GFP_KERNEL);\r
747 \r
748         if(SrcMemSize) {\r
749                 ret = rga2_MapUserMemory(&pages[0], &MMU_Base[0],
750                                          SrcStart, SrcMemSize, 0);
751             if (ret < 0) {\r
752                 pr_err("rga2 map palette memory failed\n");\r
753                 status = ret;\r
754                 break;\r
755             }\r
756 \r
757             /* change the buf address in req struct */\r
758             req->mmu_info.src0_base_addr = (((unsigned long)MMU_Base_phys));\r
759             req->pat.yrgb_addr = (req->pat.yrgb_addr & (~PAGE_MASK));\r
760         }\r
761 \r
762         /* flush data to DDR */\r
763         rga_dma_flush_range(MMU_Base, (MMU_Base + AllSize));
764         rga2_mmu_buf_get(&rga2_mmu_buf, AllSize);\r
765         reg->MMU_len = AllSize;\r
766 \r
767         return 0;\r
768     }\r
769     while(0);\r
770 \r
771     return status;\r
772 }\r
773 \r
774 static int rga2_mmu_info_update_patten_buff_mode(struct rga2_reg *reg, struct rga2_req *req)\r
775 {\r
776     int SrcMemSize, CMDMemSize;\r
777     unsigned long SrcStart, CMDStart;\r
778     struct page **pages = NULL;\r
779     uint32_t i;\r
780     uint32_t AllSize;\r
781     uint32_t *MMU_Base, *MMU_p;\r
782     int ret, status;\r
783 \r
784     MMU_Base = MMU_p = 0;\r
785 \r
786     do {\r
787         /* cal src buf mmu info */\r
788         SrcMemSize = rga2_mem_size_cal(req->pat.yrgb_addr, req->pat.act_w * req->pat.act_h * 4, &SrcStart);\r
789         if(SrcMemSize == 0) {\r
790             return -EINVAL;\r
791         }\r
792 \r
793         /* cal cmd buf mmu info */\r
794         CMDMemSize = rga2_mem_size_cal((unsigned long)rga2_service.cmd_buff, RGA2_CMD_BUF_SIZE, &CMDStart);\r
795         if(CMDMemSize == 0) {\r
796             return -EINVAL;\r
797         }\r
798 \r
799         AllSize = SrcMemSize + CMDMemSize;\r
800 \r
801         pages = rga2_mmu_buf.pages;\r
802 \r
803         MMU_Base = kzalloc(AllSize * sizeof(uint32_t), GFP_KERNEL);\r
804 \r
805         for(i=0; i<CMDMemSize; i++) {\r
806             MMU_Base[i] = virt_to_phys((uint32_t *)((CMDStart + i) << PAGE_SHIFT));\r
807         }\r
808 \r
809         if (req->src.yrgb_addr < KERNEL_SPACE_VALID)\r
810         {\r
811                 ret = rga2_MapUserMemory(&pages[CMDMemSize],
812                                          &MMU_Base[CMDMemSize],
813                                          SrcStart, SrcMemSize, 1);
814             if (ret < 0) {\r
815                 pr_err("rga map src memory failed\n");\r
816                 status = ret;\r
817                 break;\r
818             }\r
819         }\r
820         else\r
821         {\r
822             MMU_p = MMU_Base + CMDMemSize;\r
823 \r
824             for(i=0; i<SrcMemSize; i++)\r
825             {\r
826                 MMU_p[i] = (uint32_t)virt_to_phys((uint32_t *)((SrcStart + i) << PAGE_SHIFT));\r
827             }\r
828         }\r
829 \r
830         /* zsq\r
831          * change the buf address in req struct\r
832          * for the reason of lie to MMU\r
833          */\r
834         req->mmu_info.src0_base_addr = (virt_to_phys(MMU_Base) >> 2);\r
835 \r
836         req->src.yrgb_addr = (req->src.yrgb_addr & (~PAGE_MASK)) | (CMDMemSize << PAGE_SHIFT);\r
837 \r
838         /*record the malloc buf for the cmd end to release*/\r
839         reg->MMU_base = MMU_Base;\r
840 \r
841         /* flush data to DDR */\r
842         rga_dma_flush_range(MMU_Base, (MMU_Base + AllSize));
843         return 0;\r
844 \r
845     }\r
846     while(0);\r
847 \r
848     return status;\r
849 }\r
850 \r
851 int rga2_set_mmu_info(struct rga2_reg *reg, struct rga2_req *req)\r
852 {\r
853     int ret;\r
854 \r
855     switch (req->render_mode) {\r
856         case bitblt_mode :\r
857             ret = rga2_mmu_info_BitBlt_mode(reg, req);\r
858             break;\r
859         case color_palette_mode :\r
860             ret = rga2_mmu_info_color_palette_mode(reg, req);\r
861             break;\r
862         case color_fill_mode :\r
863             ret = rga2_mmu_info_color_fill_mode(reg, req);\r
864             break;\r
865         case update_palette_table_mode :\r
866             ret = rga2_mmu_info_update_palette_table_mode(reg, req);\r
867             break;\r
868         case update_patten_buff_mode :\r
869             ret = rga2_mmu_info_update_patten_buff_mode(reg, req);\r
870             break;\r
871         default :\r
872             ret = -1;\r
873             break;\r
874     }\r
875 \r
876     return ret;\r
877 }\r
878 \r