summaryrefslogtreecommitdiff
path: root/drivers/frame_provider/decoder/h264/vh264_mvc.c (plain)
blob: fdb0535ca9eb8a4618ec92bd766aa5dffaaaf4a6
1/*
2 * drivers/amlogic/amports/vh264mvc.c
3 *
4 * Copyright (C) 2015 Amlogic, Inc. All rights reserved.
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
14 * more details.
15 *
16 */
17
18#include <linux/kernel.h>
19#include <linux/types.h>
20#include <linux/errno.h>
21#include <linux/interrupt.h>
22#include <linux/timer.h>
23#include <linux/platform_device.h>
24#include <linux/amlogic/media/utils/amstream.h>
25#include <linux/amlogic/media/frame_sync/ptsserv.h>
26#include <linux/amlogic/media/canvas/canvas.h>
27#include <linux/amlogic/media/vfm/vframe.h>
28#include <linux/amlogic/media/vfm/vframe_provider.h>
29#include <linux/amlogic/media/vfm/vframe_receiver.h>
30#include <linux/amlogic/media/utils/vformat.h>
31#include <linux/workqueue.h>
32#include <linux/dma-mapping.h>
33#include <linux/atomic.h>
34#include <linux/amlogic/tee.h>
35
36#include <linux/module.h>
37#include <linux/slab.h>
38
39#include <linux/amlogic/media/utils/vdec_reg.h>
40#include "../../../stream_input/amports/amports_priv.h"
41#include "../utils/vdec.h"
42#include "../utils/amvdec.h"
43#include "../utils/decoder_mmu_box.h"
44#include "../utils/decoder_bmmu_box.h"
45#include <linux/amlogic/media/codec_mm/codec_mm.h>
46#include <linux/amlogic/media/codec_mm/configs.h>
47#include "../utils/firmware.h"
48#include <linux/amlogic/tee.h>
49
50#define TIME_TASK_PRINT_ENABLE 0x100
51#define PUT_PRINT_ENABLE 0x200
52
53#define DRIVER_NAME "amvdec_h264mvc"
54#define MODULE_NAME "amvdec_h264mvc"
55
56#define HANDLE_h264mvc_IRQ
57
58#define DEBUG_PTS
59#define DEBUG_SKIP
60
61#define PUT_INTERVAL (HZ/100)
62
63#define STAT_TIMER_INIT 0x01
64#define STAT_MC_LOAD 0x02
65#define STAT_ISR_REG 0x04
66#define STAT_VF_HOOK 0x08
67#define STAT_TIMER_ARM 0x10
68#define STAT_VDEC_RUN 0x20
69
70#define DROPPING_THREAD_HOLD 4
71#define DROPPING_FIRST_WAIT 16
72#define DISPLAY_INVALID_POS -65536
73
74#define INIT_DROP_FRAME_CNT 8
75
76static int vh264mvc_vf_states(struct vframe_states *states, void *);
77static struct vframe_s *vh264mvc_vf_peek(void *);
78static struct vframe_s *vh264mvc_vf_get(void *);
79static void vh264mvc_vf_put(struct vframe_s *, void *);
80static int vh264mvc_event_cb(int type, void *data, void *private_data);
81
82static void vh264mvc_prot_init(void);
83static int vh264mvc_local_init(void);
84static void vh264mvc_put_timer_func(unsigned long arg);
85
86static const char vh264mvc_dec_id[] = "vh264mvc-dev";
87
88#define PROVIDER_NAME "decoder.h264mvc"
89
90static struct vdec_info *gvs;
91static struct work_struct alloc_work;
92static struct work_struct set_clk_work;
93
94static DEFINE_MUTEX(vh264_mvc_mutex);
95
96static const struct vframe_operations_s vh264mvc_vf_provider = {
97 .peek = vh264mvc_vf_peek,
98 .get = vh264mvc_vf_get,
99 .put = vh264mvc_vf_put,
100 .event_cb = vh264mvc_event_cb,
101 .vf_states = vh264mvc_vf_states,
102};
103
104static struct vframe_provider_s vh264mvc_vf_prov;
105
106static u32 frame_width, frame_height, frame_dur;
107static u32 saved_resolution;
108static struct timer_list recycle_timer;
109static u32 stat;
110static u32 pts_outside;
111static u32 sync_outside;
112static u32 vh264mvc_ratio;
113static u32 h264mvc_ar;
114static u32 no_dropping_cnt;
115static s32 init_drop_cnt;
116
117#ifdef DEBUG_SKIP
118static unsigned long view_total, view_dropped;
119#endif
120
121#ifdef DEBUG_PTS
122static unsigned long pts_missed, pts_hit;
123#endif
124
125static atomic_t vh264mvc_active = ATOMIC_INIT(0);
126static struct work_struct error_wd_work;
127
128static struct dec_sysinfo vh264mvc_amstream_dec_info;
129static dma_addr_t mc_dma_handle;
130static void *mc_cpu_addr;
131
132static DEFINE_SPINLOCK(lock);
133
134static int vh264mvc_stop(void);
135static s32 vh264mvc_init(void);
136
137/***************************
138 * new
139 **************************
140 */
141
142/* bit[3:0] command : */
143/* 0 - command finished */
144/* (DATA0 - {level_idc_mmco, max_reference_frame_num, width, height} */
145/* 1 - alloc view_0 display_buffer and reference_data_area */
146/* 2 - alloc view_1 display_buffer and reference_data_area */
147#define MAILBOX_COMMAND AV_SCRATCH_0
148#define MAILBOX_DATA_0 AV_SCRATCH_1
149#define MAILBOX_DATA_1 AV_SCRATCH_2
150#define MAILBOX_DATA_2 AV_SCRATCH_3
151#define CANVAS_START AV_SCRATCH_6
152#define BUFFER_RECYCLE AV_SCRATCH_7
153#define DROP_CONTROL AV_SCRATCH_8
154#define PICTURE_COUNT AV_SCRATCH_9
155#define DECODE_STATUS AV_SCRATCH_A
156#define SPS_STATUS AV_SCRATCH_B
157#define PPS_STATUS AV_SCRATCH_C
158#define SIM_RESERV_D AV_SCRATCH_D
159#define WORKSPACE_START AV_SCRATCH_E
160#define SIM_RESERV_F AV_SCRATCH_F
161#define DECODE_ERROR_CNT AV_SCRATCH_G
162#define CURRENT_UCODE AV_SCRATCH_H
163#define CURRENT_SPS_PPS AV_SCRATCH_I/* bit[15:9]-SPS, bit[8:0]-PPS */
164#define DECODE_SKIP_PICTURE AV_SCRATCH_J
165#define UCODE_START_ADDR AV_SCRATCH_K
166#define SIM_RESERV_L AV_SCRATCH_L
167#define REF_START_VIEW_0 AV_SCRATCH_M
168#define REF_START_VIEW_1 AV_SCRATCH_N
169
170/********************************************
171 * Mailbox command
172 ********************************************/
173#define CMD_FINISHED 0
174#define CMD_ALLOC_VIEW_0 1
175#define CMD_ALLOC_VIEW_1 2
176#define CMD_FRAME_DISPLAY 3
177#define CMD_FATAL_ERROR 4
178
179#define CANVAS_INDEX_START 0x78
180/* /AMVDEC_H264MVC_CANVAS_INDEX */
181
182#define MC_TOTAL_SIZE (28*SZ_1K)
183#define MC_SWAP_SIZE (4*SZ_1K)
184
185unsigned int DECODE_BUFFER_START = 0x00200000;
186unsigned int DECODE_BUFFER_END = 0x05000000;
187
188#define DECODE_BUFFER_NUM_MAX 16
189#define DISPLAY_BUFFER_NUM 4
190#define MAX_BMMU_BUFFER_NUM (DECODE_BUFFER_NUM_MAX + DISPLAY_BUFFER_NUM)
191#define TOTAL_BMMU_BUFF_NUM (MAX_BMMU_BUFFER_NUM * 2 + 3)
192#define VF_BUFFER_IDX(n) (2 + n)
193
194#define DECODER_WORK_SPACE_SIZE 0xa0000
195
196
197static unsigned int ANC_CANVAS_ADDR;
198static unsigned int index;
199static unsigned long ref_start_addr[2];
200static unsigned int max_dec_frame_buffering[2];
201static unsigned int total_dec_frame_buffering[2];
202
203static unsigned int dpb_size, ref_size;
204
205static int display_buff_id;
206static int display_view_id;
207static int display_POC;
208static int stream_offset;
209
210#define video_domain_addr(adr) (adr&0x7fffffff)
211static unsigned long work_space_adr;
212
213struct buffer_spec_s {
214 unsigned int y_addr;
215 unsigned int u_addr;
216 unsigned int v_addr;
217
218 int y_canvas_index;
219 int u_canvas_index;
220 int v_canvas_index;
221
222 struct page *alloc_pages;
223 unsigned long phy_addr;
224 int alloc_count;
225};
226static struct buffer_spec_s buffer_spec0[MAX_BMMU_BUFFER_NUM];
227static struct buffer_spec_s buffer_spec1[MAX_BMMU_BUFFER_NUM];
228static void *mm_blk_handle;
229
230/*
231 * dbg_mode:
232 * bit 0: 1, print debug information
233 * bit 4: 1, recycle buffer without displaying;
234 * bit 5: 1, buffer single frame step , set dbg_cmd to 1 to step
235 *
236 */
237static int dbg_mode;
238static int dbg_cmd;
239static int view_mode =
240 3; /* 0, left; 1 ,right ; 2, left<->right 3, right<->left */
241static int drop_rate = 2;
242static int drop_thread_hold;
243/**/
244
245struct mvc_buf_s {
246 struct list_head list;
247 struct vframe_s vframe;
248 int display_POC;
249 int view0_buff_id;
250 int view1_buff_id;
251 int view0_drop;
252 int view1_drop;
253 int stream_offset;
254 unsigned int pts;
255} /*mvc_buf_t */;
256
257#define spec2canvas(x) \
258 (((x)->v_canvas_index << 16) | \
259 ((x)->u_canvas_index << 8) | \
260 ((x)->y_canvas_index << 0))
261
262#define to_mvcbuf(vf) \
263 container_of(vf, struct mvc_buf_s, vframe)
264
265static int vf_buf_init_flag;
266
267static void init_vf_buf(void)
268{
269
270 vf_buf_init_flag = 1;
271}
272
273static void uninit_vf_buf(void)
274{
275
276}
277
278/* #define QUEUE_SUPPORT */
279
280struct mvc_info_s {
281 int view0_buf_id;
282 int view1_buf_id;
283 int view0_drop;
284 int view1_drop;
285 int display_pos;
286 int used;
287 int slot;
288 unsigned int stream_offset;
289};
290
291#define VF_POOL_SIZE 20
292static struct vframe_s vfpool[VF_POOL_SIZE];
293static struct mvc_info_s vfpool_idx[VF_POOL_SIZE];
294static s32 view0_vfbuf_use[DECODE_BUFFER_NUM_MAX];
295static s32 view1_vfbuf_use[DECODE_BUFFER_NUM_MAX];
296
297static s32 fill_ptr, get_ptr, putting_ptr, put_ptr;
298static s32 dirty_frame_num;
299static s32 enable_recycle;
300
301static s32 init_drop_frame_id[INIT_DROP_FRAME_CNT];
302#define INCPTR(p) ptr_atomic_wrap_inc(&p)
303static inline void ptr_atomic_wrap_inc(u32 *ptr)
304{
305 u32 i = *ptr;
306
307 i++;
308
309 if (i >= VF_POOL_SIZE)
310 i = 0;
311
312 *ptr = i;
313}
314
315static void set_frame_info(struct vframe_s *vf)
316{
317 unsigned int ar = 0;
318
319 vf->width = frame_width;
320 vf->height = frame_height;
321 vf->duration = frame_dur;
322 vf->duration_pulldown = 0;
323
324 if (vh264mvc_ratio == 0) {
325 /* always stretch to 16:9 */
326 vf->ratio_control |= (0x90 <<
327 DISP_RATIO_ASPECT_RATIO_BIT);
328 } else {
329 /* h264mvc_ar = ((float)frame_height/frame_width)
330 *customer_ratio;
331 */
332 ar = min_t(u32, h264mvc_ar, DISP_RATIO_ASPECT_RATIO_MAX);
333
334 vf->ratio_control = (ar << DISP_RATIO_ASPECT_RATIO_BIT);
335 }
336}
337
338static int vh264mvc_vf_states(struct vframe_states *states, void *op_arg)
339{
340 unsigned long flags;
341 int i;
342
343 spin_lock_irqsave(&lock, flags);
344 states->vf_pool_size = VF_POOL_SIZE;
345
346 i = put_ptr - fill_ptr;
347 if (i < 0)
348 i += VF_POOL_SIZE;
349 states->buf_free_num = i;
350
351 i = putting_ptr - put_ptr;
352 if (i < 0)
353 i += VF_POOL_SIZE;
354 states->buf_recycle_num = i;
355
356 i = fill_ptr - get_ptr;
357 if (i < 0)
358 i += VF_POOL_SIZE;
359 states->buf_avail_num = i;
360
361 spin_unlock_irqrestore(&lock, flags);
362 return 0;
363}
364
365void send_drop_cmd(void)
366{
367 int ready_cnt = 0;
368 int temp_get_ptr = get_ptr;
369 int temp_fill_ptr = fill_ptr;
370
371 while (temp_get_ptr != temp_fill_ptr) {
372 if ((vfpool_idx[temp_get_ptr].view0_buf_id >= 0)
373 && (vfpool_idx[temp_get_ptr].view1_buf_id >= 0)
374 && (vfpool_idx[temp_get_ptr].view0_drop == 0)
375 && (vfpool_idx[temp_get_ptr].view1_drop == 0))
376 ready_cnt++;
377 INCPTR(temp_get_ptr);
378 }
379 if (dbg_mode & 0x40) {
380 pr_info("ready_cnt is %d ; no_dropping_cnt is %d\n", ready_cnt,
381 no_dropping_cnt);
382 }
383 if ((no_dropping_cnt >= DROPPING_FIRST_WAIT)
384 && (ready_cnt < drop_thread_hold))
385 WRITE_VREG(DROP_CONTROL, (1 << 31) | (drop_rate));
386 else
387 WRITE_VREG(DROP_CONTROL, 0);
388}
389
390#if 0
391int get_valid_frame(void)
392{
393 int ready_cnt = 0;
394 int temp_get_ptr = get_ptr;
395 int temp_fill_ptr = fill_ptr;
396
397 while (temp_get_ptr != temp_fill_ptr) {
398 if ((vfpool_idx[temp_get_ptr].view0_buf_id >= 0)
399 && (vfpool_idx[temp_get_ptr].view1_buf_id >= 0)
400 && (vfpool_idx[temp_get_ptr].view0_drop == 0)
401 && (vfpool_idx[temp_get_ptr].view1_drop == 0))
402 ready_cnt++;
403 INCPTR(temp_get_ptr);
404 }
405 return ready_cnt;
406}
407#endif
408static struct vframe_s *vh264mvc_vf_peek(void *op_arg)
409{
410
411 if (get_ptr == fill_ptr)
412 return NULL;
413 send_drop_cmd();
414 return &vfpool[get_ptr];
415
416}
417
418static struct vframe_s *vh264mvc_vf_get(void *op_arg)
419{
420
421 struct vframe_s *vf;
422 int view0_buf_id;
423 int view1_buf_id;
424
425 if (get_ptr == fill_ptr)
426 return NULL;
427
428 view0_buf_id = vfpool_idx[get_ptr].view0_buf_id;
429 view1_buf_id = vfpool_idx[get_ptr].view1_buf_id;
430 vf = &vfpool[get_ptr];
431
432 if ((view0_buf_id >= 0) && (view1_buf_id >= 0)) {
433 if (view_mode == 0 || view_mode == 1) {
434 vf->type = VIDTYPE_PROGRESSIVE | VIDTYPE_VIU_FIELD;
435 vf->canvas0Addr = vf->canvas1Addr =
436 (view_mode ==
437 0) ? spec2canvas(&buffer_spec0[view0_buf_id]) :
438 spec2canvas(&buffer_spec1[view1_buf_id]);
439 } else {
440 vf->type = VIDTYPE_PROGRESSIVE | VIDTYPE_MVC;
441
442 vf->left_eye.start_x = 0;
443 vf->left_eye.start_y = 0;
444 vf->left_eye.width = vf->width;
445 vf->left_eye.height = vf->height;
446 vf->right_eye.start_x = 0;
447 vf->right_eye.start_y = 0;
448 vf->right_eye.width = vf->width;
449 vf->right_eye.height = vf->height;
450 vf->trans_fmt = TVIN_TFMT_3D_TB;
451
452 if (view_mode == 2) {
453 vf->canvas0Addr =
454 spec2canvas(&buffer_spec1[
455 view1_buf_id]);
456 vf->canvas1Addr =
457 spec2canvas(&buffer_spec0[
458 view0_buf_id]);
459 } else {
460 vf->canvas0Addr =
461 spec2canvas(&buffer_spec0[
462 view0_buf_id]);
463 vf->canvas1Addr =
464 spec2canvas(&buffer_spec1[
465 view1_buf_id]);
466 }
467 }
468 }
469 vf->type_original = vf->type;
470 if (((vfpool_idx[get_ptr].view0_drop != 0)
471 || (vfpool_idx[get_ptr].view1_drop != 0))
472 && ((no_dropping_cnt >= DROPPING_FIRST_WAIT)))
473 vf->frame_dirty = 1;
474 else
475 vf->frame_dirty = 0;
476
477 INCPTR(get_ptr);
478
479 if (frame_width == 0)
480 frame_width = vh264mvc_amstream_dec_info.width;
481 if (frame_height == 0)
482 frame_height = vh264mvc_amstream_dec_info.height;
483
484 vf->width = frame_width;
485 vf->height = frame_height;
486
487 if ((no_dropping_cnt < DROPPING_FIRST_WAIT) && (vf->frame_dirty == 0))
488 no_dropping_cnt++;
489 return vf;
490
491}
492
493static void vh264mvc_vf_put(struct vframe_s *vf, void *op_arg)
494{
495
496 if (vf_buf_init_flag == 0)
497 return;
498 if (vf->frame_dirty) {
499
500 vf->frame_dirty = 0;
501 dirty_frame_num++;
502 enable_recycle = 0;
503 if (dbg_mode & PUT_PRINT_ENABLE) {
504 pr_info("invalid: dirty_frame_num is !!! %d\n",
505 dirty_frame_num);
506 }
507 } else {
508 INCPTR(putting_ptr);
509 while (dirty_frame_num > 0) {
510 INCPTR(putting_ptr);
511 dirty_frame_num--;
512 }
513 enable_recycle = 1;
514 if (dbg_mode & PUT_PRINT_ENABLE) {
515 pr_info("valid: dirty_frame_num is @@@ %d\n",
516 dirty_frame_num);
517 }
518 /* send_drop_cmd(); */
519 }
520
521}
522
523static int vh264mvc_event_cb(int type, void *data, void *private_data)
524{
525 if (type & VFRAME_EVENT_RECEIVER_RESET) {
526 unsigned long flags;
527
528 amvdec_stop();
529#ifndef CONFIG_AMLOGIC_POST_PROCESS_MANAGER
530 vf_light_unreg_provider(&vh264mvc_vf_prov);
531#endif
532 spin_lock_irqsave(&lock, flags);
533 vh264mvc_local_init();
534 vh264mvc_prot_init();
535 spin_unlock_irqrestore(&lock, flags);
536#ifndef CONFIG_AMLOGIC_POST_PROCESS_MANAGER
537 vf_reg_provider(&vh264mvc_vf_prov);
538#endif
539 amvdec_start();
540 }
541 return 0;
542}
543
544/**/
545static long init_canvas(int view_index, int refbuf_size, long dpb_size,
546 int dpb_number, int mb_width, int mb_height,
547 struct buffer_spec_s *buffer_spec)
548{
549
550 unsigned long addr;
551 int i, j, bmmu_index;
552 int mb_total, ret = -1;
553 /* cav_con canvas; */
554 mb_total = mb_width * mb_height;
555 mutex_lock(&vh264_mvc_mutex);
556
557 for (j = 0; j < (dpb_number + 1); j++) {
558 int page_count;
559 if (j == 0) {
560 if (!view_index)
561 bmmu_index = 1;
562 else
563 bmmu_index = dpb_number + 2;
564
565 ret = decoder_bmmu_box_alloc_buf_phy(mm_blk_handle,
566 bmmu_index, refbuf_size, DRIVER_NAME,
567 &ref_start_addr[view_index]);
568
569 if (ret < 0) {
570 mutex_unlock(&vh264_mvc_mutex);
571 return ret;
572 }
573
574 continue;
575 }
576 /* canvas buf */
577 WRITE_VREG(ANC_CANVAS_ADDR,
578 index | ((index + 1) << 8) |
579 ((index + 2) << 16));
580 ANC_CANVAS_ADDR++;
581
582 i = j - 1;
583 if (!view_index)
584 bmmu_index = VF_BUFFER_IDX(i);
585 else
586 bmmu_index = VF_BUFFER_IDX(i) + dpb_number + 1;
587#ifdef DOUBLE_WRITE
588 page_count = PAGE_ALIGN((mb_total << 8) + (mb_total << 7) +
589 (mb_total << 6) + (mb_total << 5)) / PAGE_SIZE;
590#else
591 page_count = PAGE_ALIGN((mb_total << 8) +
592 (mb_total << 7)) / PAGE_SIZE;
593#endif
594
595 ret = decoder_bmmu_box_alloc_buf_phy(mm_blk_handle,
596 bmmu_index, page_count << PAGE_SHIFT,
597 DRIVER_NAME, &buffer_spec[i].phy_addr);
598
599 if (ret < 0) {
600 buffer_spec[i].alloc_count = 0;
601 mutex_unlock(&vh264_mvc_mutex);
602 return ret;
603 }
604
605 addr = buffer_spec[i].phy_addr;
606 buffer_spec[i].alloc_count = page_count;
607 buffer_spec[i].y_addr = addr;
608 buffer_spec[i].y_canvas_index = index;
609 canvas_config(index, addr,
610 mb_width << 4, mb_height << 4,
611 CANVAS_ADDR_NOWRAP, CANVAS_BLKMODE_32X32);
612
613 addr += mb_total << 8;
614 index++;
615 buffer_spec[i].u_addr = addr;
616 buffer_spec[i].u_canvas_index = index;
617 canvas_config(index, addr, mb_width << 3, mb_height << 3,
618 CANVAS_ADDR_NOWRAP, CANVAS_BLKMODE_32X32);
619
620 addr += mb_total << 6;
621 index++;
622 buffer_spec[i].v_addr = addr;
623 buffer_spec[i].v_canvas_index = index;
624 canvas_config(index, addr, mb_width << 3, mb_height << 3,
625 CANVAS_ADDR_NOWRAP, CANVAS_BLKMODE_32X32);
626
627 index++;
628 }
629 mutex_unlock(&vh264_mvc_mutex);
630 return 0;
631}
632
633static int get_max_dec_frame_buf_size(int level_idc,
634 int max_reference_frame_num, int mb_width,
635 int mb_height)
636{
637 int pic_size = mb_width * mb_height * 384;
638
639 int size = 0;
640
641 switch (level_idc) {
642 case 9:
643 size = 152064;
644 break;
645 case 10:
646 size = 152064;
647 break;
648 case 11:
649 size = 345600;
650 break;
651 case 12:
652 size = 912384;
653 break;
654 case 13:
655 size = 912384;
656 break;
657 case 20:
658 size = 912384;
659 break;
660 case 21:
661 size = 1824768;
662 break;
663 case 22:
664 size = 3110400;
665 break;
666 case 30:
667 size = 3110400;
668 break;
669 case 31:
670 size = 6912000;
671 break;
672 case 32:
673 size = 7864320;
674 break;
675 case 40:
676 size = 12582912;
677 break;
678 case 41:
679 size = 12582912;
680 break;
681 case 42:
682 size = 13369344;
683 break;
684 case 50:
685 size = 42393600;
686 break;
687 case 51:
688 size = 70778880;
689 break;
690 default:
691 break;
692 }
693
694 size /= pic_size;
695 size = size + 1; /* For MVC need onr more buffer */
696 if (max_reference_frame_num > size)
697 size = max_reference_frame_num;
698 if (size > DECODE_BUFFER_NUM_MAX)
699 size = DECODE_BUFFER_NUM_MAX;
700
701 return size;
702}
703
704int check_in_list(int pos, int *slot)
705{
706 int i;
707 int ret = 0;
708
709 for (i = 0; i < VF_POOL_SIZE; i++) {
710 if ((vfpool_idx[i].display_pos == pos)
711 && (vfpool_idx[i].used == 0)) {
712 ret = 1;
713 *slot = vfpool_idx[i].slot;
714 break;
715 }
716 }
717 return ret;
718}
719
720static void do_alloc_work(struct work_struct *work)
721{
722 int level_idc, max_reference_frame_num, mb_width, mb_height;
723 int refbuf_size;
724 int ret = READ_VREG(MAILBOX_COMMAND);
725
726 switch (ret & 0xff) {
727 case CMD_ALLOC_VIEW_0:
728 if (dbg_mode & 0x1) {
729 pr_info
730 ("Start H264 display buffer for view 0\n");
731 }
732
733 ret = READ_VREG(MAILBOX_DATA_0);
734 level_idc = (ret >> 24) & 0xff;
735 max_reference_frame_num = (ret >> 16) & 0xff;
736 mb_width = (ret >> 8) & 0xff;
737 mb_height = (ret >> 0) & 0xff;
738 max_dec_frame_buffering[0] =
739 get_max_dec_frame_buf_size(level_idc,
740 max_reference_frame_num,
741 mb_width, mb_height);
742
743 total_dec_frame_buffering[0] =
744 max_dec_frame_buffering[0] + DISPLAY_BUFFER_NUM;
745
746 mb_width = (mb_width + 3) & 0xfffffffc;
747 mb_height = (mb_height + 3) & 0xfffffffc;
748
749 dpb_size = mb_width * mb_height * 384;
750 ref_size = mb_width * mb_height * 96;
751
752 if (dbg_mode & 0x1) {
753 pr_info("dpb_size: 0x%x\n", dpb_size);
754 pr_info("ref_size: 0x%x\n", ref_size);
755 pr_info("total_dec_frame_buffering[0] : 0x%x\n",
756 total_dec_frame_buffering[0]);
757 pr_info("max_reference_frame_num: 0x%x\n",
758 max_reference_frame_num);
759 }
760 refbuf_size
761 = ref_size * (max_reference_frame_num + 1) * 2;
762
763 index = CANVAS_INDEX_START;
764 ANC_CANVAS_ADDR = ANC0_CANVAS_ADDR;
765
766 ret =
767 init_canvas(0, refbuf_size, dpb_size,
768 total_dec_frame_buffering[0], mb_width,
769 mb_height, buffer_spec0);
770
771 if (ret < 0) {
772 pr_info(" Un-expected memory alloc problem\n");
773 return;
774 }
775
776 WRITE_VREG(REF_START_VIEW_0,
777 video_domain_addr(ref_start_addr[0]));
778 WRITE_VREG(MAILBOX_DATA_0,
779 (max_dec_frame_buffering[0] << 8) |
780 (total_dec_frame_buffering[0] << 0));
781 WRITE_VREG(MAILBOX_DATA_1, ref_size);
782 WRITE_VREG(MAILBOX_COMMAND, CMD_FINISHED);
783
784 if (dbg_mode & 0x1) {
785 pr_info
786 ("End H264 display buffer for view 0\n");
787 }
788 if (frame_width == 0) {
789 if (vh264mvc_amstream_dec_info.width)
790 frame_width = vh264mvc_amstream_dec_info.width;
791 else
792 frame_width = mb_width << 4;
793 }
794 if (frame_height == 0) {
795 frame_height = mb_height << 4;
796 if (frame_height == 1088)
797 frame_height = 1080;
798 }
799 break;
800 case CMD_ALLOC_VIEW_1:
801 if (dbg_mode & 0x1) {
802 pr_info
803 ("Start H264 display buffer for view 1\n");
804 }
805
806 ret = READ_VREG(MAILBOX_DATA_0);
807 level_idc = (ret >> 24) & 0xff;
808 max_reference_frame_num = (ret >> 16) & 0xff;
809 mb_width = (ret >> 8) & 0xff;
810 mb_height = (ret >> 0) & 0xff;
811 max_dec_frame_buffering[1] =
812 get_max_dec_frame_buf_size(level_idc,
813 max_reference_frame_num,
814 mb_width, mb_height);
815 if (max_dec_frame_buffering[1] != max_dec_frame_buffering[0]) {
816 pr_info
817 (" Warning: view0/1 max_dec_frame_buffering ");
818 pr_info("different : 0x%x/0x%x, Use View0\n",
819 max_dec_frame_buffering[0],
820 max_dec_frame_buffering[1]);
821 max_dec_frame_buffering[1] = max_dec_frame_buffering[0];
822 }
823
824 total_dec_frame_buffering[1] =
825 max_dec_frame_buffering[1] + DISPLAY_BUFFER_NUM;
826
827 mb_width = (mb_width + 3) & 0xfffffffc;
828 mb_height = (mb_height + 3) & 0xfffffffc;
829
830 dpb_size = mb_width * mb_height * 384;
831 ref_size = mb_width * mb_height * 96;
832 refbuf_size = ref_size * (max_reference_frame_num + 1) * 2;
833 if (dbg_mode & 0x1) {
834 pr_info("dpb_size: 0x%x\n", dpb_size);
835 pr_info("ref_size: 0x%x\n", ref_size);
836 pr_info("total_dec_frame_buffering[1] : 0x%x\n",
837 total_dec_frame_buffering[1]);
838 pr_info("max_reference_frame_num: 0x%x\n",
839 max_reference_frame_num);
840 }
841
842 index = CANVAS_INDEX_START + total_dec_frame_buffering[0] * 3;
843 ANC_CANVAS_ADDR =
844 ANC0_CANVAS_ADDR + total_dec_frame_buffering[0];
845
846 ret = init_canvas(1, refbuf_size, dpb_size,
847 total_dec_frame_buffering[1], mb_width,
848 mb_height, buffer_spec1);
849
850 if (ret < 0) {
851 pr_info(" Un-expected memory alloc problem\n");
852 return;
853 }
854
855 WRITE_VREG(REF_START_VIEW_1,
856 video_domain_addr(ref_start_addr[1]));
857 WRITE_VREG(MAILBOX_DATA_0,
858 (max_dec_frame_buffering[1] << 8) |
859 (total_dec_frame_buffering[1] << 0));
860 WRITE_VREG(MAILBOX_DATA_1, ref_size);
861 WRITE_VREG(MAILBOX_COMMAND, CMD_FINISHED);
862
863 if (dbg_mode & 0x1) {
864 pr_info
865 ("End H264 buffer allocation for view 1\n");
866 }
867 if (frame_width == 0) {
868 if (vh264mvc_amstream_dec_info.width)
869 frame_width = vh264mvc_amstream_dec_info.width;
870 else
871 frame_width = mb_width << 4;
872 }
873 if (frame_height == 0) {
874 frame_height = mb_height << 4;
875 if (frame_height == 1088)
876 frame_height = 1080;
877 }
878 break;
879 }
880
881}
882
883
884#ifdef HANDLE_h264mvc_IRQ
885static irqreturn_t vh264mvc_isr(int irq, void *dev_id)
886#else
887static void vh264mvc_isr(void)
888#endif
889{
890 int drop_status;
891 struct vframe_s *vf;
892 unsigned int pts, pts_valid = 0;
893 u64 pts_us64;
894 u32 frame_size;
895 int ret = READ_VREG(MAILBOX_COMMAND);
896 /* pr_info("vh264mvc_isr, cmd =%x\n", ret); */
897 switch (ret & 0xff) {
898 case CMD_ALLOC_VIEW_0:
899 case CMD_ALLOC_VIEW_1:
900 schedule_work(&alloc_work);
901 break;
902 case CMD_FRAME_DISPLAY:
903 ret = READ_VREG(MAILBOX_DATA_0);
904 display_buff_id = (ret >> 0) & 0x3f;
905 display_view_id = (ret >> 6) & 0x3;
906 drop_status = (ret >> 8) & 0x1;
907 display_POC = READ_VREG(MAILBOX_DATA_1);
908 stream_offset = READ_VREG(MAILBOX_DATA_2);
909 /* if (display_view_id == 0) */
910 WRITE_VREG(MAILBOX_COMMAND, CMD_FINISHED);
911
912#ifdef DEBUG_SKIP
913 view_total++;
914 if (drop_status)
915 view_dropped++;
916#endif
917 if (dbg_mode & 0x1) {
918 pr_info
919 (" H264 display frame ready - View : %x, Buffer : %x\n",
920 display_view_id, display_buff_id);
921 pr_info
922 (" H264 display frame POC -- Buffer : %x, POC : %x\n",
923 display_buff_id, display_POC);
924 pr_info("H264 display frame ready\n");
925 }
926 if (dbg_mode & 0x10) {
927 if ((dbg_mode & 0x20) == 0) {
928 while (READ_VREG(BUFFER_RECYCLE) != 0)
929 ;
930 WRITE_VREG(BUFFER_RECYCLE,
931 (display_view_id << 8) |
932 (display_buff_id + 1));
933 display_buff_id = -1;
934 display_view_id = -1;
935 display_POC = -1;
936 }
937 } else {
938 unsigned char in_list_flag = 0;
939
940 int slot = 0;
941
942 in_list_flag = check_in_list(display_POC, &slot);
943
944 if ((dbg_mode & 0x40) && (drop_status)) {
945 pr_info
946 ("drop_status:%dview_id=%d,buff_id=%d,",
947 drop_status, display_view_id, display_buff_id);
948 pr_info
949 ("offset=%d, display_POC = %d,fill_ptr=0x%x\n",
950 stream_offset, display_POC, fill_ptr);
951 }
952
953 if ((in_list_flag) && (stream_offset != 0)) {
954 pr_info
955 ("error case ,display_POC is %d, slot is %d\n",
956 display_POC, slot);
957 in_list_flag = 0;
958 }
959 if (!in_list_flag) {
960 if (display_view_id == 0) {
961 vfpool_idx[fill_ptr].view0_buf_id =
962 display_buff_id;
963 view0_vfbuf_use[display_buff_id]++;
964 vfpool_idx[fill_ptr].stream_offset =
965 stream_offset;
966 vfpool_idx[fill_ptr].view0_drop =
967 drop_status;
968 }
969 if (display_view_id == 1) {
970 vfpool_idx[fill_ptr].view1_buf_id =
971 display_buff_id;
972 vfpool_idx[fill_ptr].view1_drop =
973 drop_status;
974 view1_vfbuf_use[display_buff_id]++;
975 }
976 vfpool_idx[fill_ptr].slot = fill_ptr;
977 vfpool_idx[fill_ptr].display_pos = display_POC;
978
979 } else {
980 if (display_view_id == 0) {
981 vfpool_idx[slot].view0_buf_id =
982 display_buff_id;
983 view0_vfbuf_use[display_buff_id]++;
984 vfpool_idx[slot].stream_offset =
985 stream_offset;
986 vfpool_idx[slot].view0_drop =
987 drop_status;
988
989 }
990 if (display_view_id == 1) {
991 vfpool_idx[slot].view1_buf_id =
992 display_buff_id;
993 view1_vfbuf_use[display_buff_id]++;
994 vfpool_idx[slot].view1_drop =
995 drop_status;
996 }
997 vf = &vfpool[slot];
998
999 if (display_view_id == 0) {
1000 vf->mem_handle =
1001 decoder_bmmu_box_get_mem_handle(
1002 mm_blk_handle,
1003 VF_BUFFER_IDX(display_buff_id));
1004
1005 } else if (display_view_id == 1) {
1006 vf->mem_head_handle =
1007 decoder_bmmu_box_get_mem_handle(
1008 mm_blk_handle,
1009 VF_BUFFER_IDX(display_buff_id));
1010
1011 vf->mem_handle =
1012 decoder_bmmu_box_get_mem_handle(
1013 mm_blk_handle,
1014 VF_BUFFER_IDX(display_buff_id)
1015 + total_dec_frame_buffering[0]
1016 + 1);
1017 }
1018
1019
1020
1021 if (vfpool_idx[slot].stream_offset == 0) {
1022 pr_info
1023 ("error case, invalid stream offset\n");
1024 }
1025 if (pts_lookup_offset_us64
1026 (PTS_TYPE_VIDEO,
1027 vfpool_idx[slot].stream_offset, &pts,
1028 &frame_size,
1029 0x10000, &pts_us64) == 0)
1030 pts_valid = 1;
1031 else
1032 pts_valid = 0;
1033 vf->pts = (pts_valid) ? pts : 0;
1034 vf->pts_us64 = (pts_valid) ? pts_us64 : 0;
1035 /* vf->pts = vf->pts_us64 ? vf->pts_us64
1036 * : vf->pts ;
1037 */
1038 /* vf->pts = vf->pts_us64; */
1039 if (dbg_mode & 0x80)
1040 pr_info("vf->pts:%d\n", vf->pts);
1041 vfpool_idx[slot].used = 1;
1042 INCPTR(fill_ptr);
1043 set_frame_info(vf);
1044
1045 gvs->frame_dur = frame_dur;
1046 vdec_count_info(gvs, 0,
1047 vfpool_idx[slot].stream_offset);
1048
1049 vf_notify_receiver(PROVIDER_NAME,
1050 VFRAME_EVENT_PROVIDER_VFRAME_READY,
1051 NULL);
1052
1053 }
1054 }
1055 break;
1056 case CMD_FATAL_ERROR:
1057 pr_info("fatal error !!!\n");
1058 schedule_work(&error_wd_work);
1059 break;
1060 default:
1061 break;
1062 }
1063#ifdef HANDLE_h264mvc_IRQ
1064 return IRQ_HANDLED;
1065#else
1066 return;
1067#endif
1068}
1069
1070static void vh264_mvc_set_clk(struct work_struct *work)
1071{
1072 if (frame_dur > 0 && saved_resolution !=
1073 frame_width * frame_height * (96000 / frame_dur)) {
1074 int fps = 96000 / frame_dur;
1075
1076 saved_resolution = frame_width * frame_height * fps;
1077 vdec_source_changed(VFORMAT_H264MVC,
1078 frame_width, frame_height, fps * 2);
1079 }
1080}
1081
1082static void vh264mvc_put_timer_func(unsigned long arg)
1083{
1084 struct timer_list *timer = (struct timer_list *)arg;
1085
1086 int valid_frame = 0;
1087
1088 if (enable_recycle == 0) {
1089 if (dbg_mode & TIME_TASK_PRINT_ENABLE) {
1090 /* valid_frame = get_valid_frame(); */
1091 pr_info("dirty_frame_num is %d , valid frame is %d\n",
1092 dirty_frame_num, valid_frame);
1093
1094 }
1095 /* goto RESTART; */
1096 }
1097
1098 while ((putting_ptr != put_ptr) && (READ_VREG(BUFFER_RECYCLE) == 0)) {
1099 int view0_buf_id = vfpool_idx[put_ptr].view0_buf_id;
1100 int view1_buf_id = vfpool_idx[put_ptr].view1_buf_id;
1101
1102 if ((view0_buf_id >= 0) &&
1103 (view0_vfbuf_use[view0_buf_id] == 1)) {
1104 if (dbg_mode & 0x100) {
1105 pr_info
1106 ("round 0: put_ptr is %d ;view0_buf_id is %d\n",
1107 put_ptr, view0_buf_id);
1108 }
1109 WRITE_VREG(BUFFER_RECYCLE,
1110 (0 << 8) | (view0_buf_id + 1));
1111 view0_vfbuf_use[view0_buf_id] = 0;
1112 vfpool_idx[put_ptr].view0_buf_id = -1;
1113 vfpool_idx[put_ptr].view0_drop = 0;
1114 } else if ((view1_buf_id >= 0)
1115 && (view1_vfbuf_use[view1_buf_id] == 1)) {
1116 if (dbg_mode & 0x100) {
1117 pr_info
1118 ("round 1: put_ptr is %d ;view1_buf_id %d==\n",
1119 put_ptr, view1_buf_id);
1120 }
1121 WRITE_VREG(BUFFER_RECYCLE,
1122 (1 << 8) | (view1_buf_id + 1));
1123 view1_vfbuf_use[view1_buf_id] = 0;
1124 vfpool_idx[put_ptr].display_pos = DISPLAY_INVALID_POS;
1125 vfpool_idx[put_ptr].view1_buf_id = -1;
1126 vfpool_idx[put_ptr].view1_drop = 0;
1127 vfpool_idx[put_ptr].used = 0;
1128 INCPTR(put_ptr);
1129 }
1130 }
1131
1132 schedule_work(&set_clk_work);
1133
1134 /* RESTART: */
1135 timer->expires = jiffies + PUT_INTERVAL;
1136
1137 add_timer(timer);
1138}
1139
1140int vh264mvc_dec_status(struct vdec_s *vdec, struct vdec_info *vstatus)
1141{
1142 vstatus->frame_width = frame_width;
1143 vstatus->frame_height = frame_height;
1144 if (frame_dur != 0)
1145 vstatus->frame_rate = 96000 / frame_dur;
1146 else
1147 vstatus->frame_rate = -1;
1148 vstatus->error_count = READ_VREG(AV_SCRATCH_D);
1149 vstatus->status = stat;
1150 vstatus->bit_rate = gvs->bit_rate;
1151 vstatus->frame_dur = frame_dur;
1152 vstatus->frame_data = gvs->frame_data;
1153 vstatus->total_data = gvs->total_data;
1154 vstatus->frame_count = gvs->frame_count;
1155 vstatus->error_frame_count = gvs->error_frame_count;
1156 vstatus->drop_frame_count = gvs->drop_frame_count;
1157 vstatus->total_data = gvs->total_data;
1158 vstatus->samp_cnt = gvs->samp_cnt;
1159 vstatus->offset = gvs->offset;
1160 snprintf(vstatus->vdec_name, sizeof(vstatus->vdec_name),
1161 "%s", DRIVER_NAME);
1162
1163 return 0;
1164}
1165
1166static int vh264mvc_vdec_info_init(void)
1167{
1168 gvs = kzalloc(sizeof(struct vdec_info), GFP_KERNEL);
1169 if (NULL == gvs) {
1170 pr_info("the struct of vdec status malloc failed.\n");
1171 return -ENOMEM;
1172 }
1173 return 0;
1174}
1175
1176int vh264mvc_set_trickmode(struct vdec_s *vdec, unsigned long trickmode)
1177{
1178 if (trickmode == TRICKMODE_I) {
1179 WRITE_VREG(AV_SCRATCH_F,
1180 (READ_VREG(AV_SCRATCH_F) & 0xfffffffc) | 2);
1181 trickmode_i = 1;
1182 } else if (trickmode == TRICKMODE_NONE) {
1183 WRITE_VREG(AV_SCRATCH_F, READ_VREG(AV_SCRATCH_F) & 0xfffffffc);
1184 trickmode_i = 0;
1185 }
1186
1187 return 0;
1188}
1189
1190static void H264_DECODE_INIT(void)
1191{
1192 int i;
1193
1194 i = READ_VREG(DECODE_SKIP_PICTURE);
1195
1196#if 1 /* /MESON_CPU_TYPE >= MESON_CPU_TYPE_MESON6 */
1197 WRITE_VREG(DOS_SW_RESET0, (1 << 7) | (1 << 6) | (1 << 4));
1198 WRITE_VREG(DOS_SW_RESET0, 0);
1199
1200 READ_VREG(DOS_SW_RESET0);
1201 READ_VREG(DOS_SW_RESET0);
1202 READ_VREG(DOS_SW_RESET0);
1203
1204 WRITE_VREG(DOS_SW_RESET0, (1 << 7) | (1 << 6) | (1 << 4));
1205 WRITE_VREG(DOS_SW_RESET0, 0);
1206
1207 WRITE_VREG(DOS_SW_RESET0, (1 << 9) | (1 << 8));
1208 WRITE_VREG(DOS_SW_RESET0, 0);
1209
1210 READ_VREG(DOS_SW_RESET0);
1211 READ_VREG(DOS_SW_RESET0);
1212 READ_VREG(DOS_SW_RESET0);
1213
1214#else
1215 WRITE_RESET_REG(RESET0_REGISTER,
1216 RESET_IQIDCT | RESET_MC | RESET_VLD_PART);
1217 READ_RESET_REG(RESET0_REGISTER);
1218 WRITE_RESET_REG(RESET0_REGISTER,
1219 RESET_IQIDCT | RESET_MC | RESET_VLD_PART);
1220 WRITE_RESET_REG(RESET2_REGISTER, RESET_PIC_DC | RESET_DBLK);
1221#endif
1222
1223 /* Wait for some time for RESET */
1224 READ_VREG(DECODE_SKIP_PICTURE);
1225 READ_VREG(DECODE_SKIP_PICTURE);
1226
1227 WRITE_VREG(DECODE_SKIP_PICTURE, i);
1228
1229 /* fill_weight_pred */
1230 WRITE_VREG(MC_MPORT_CTRL, 0x0300);
1231 for (i = 0; i < 192; i++)
1232 WRITE_VREG(MC_MPORT_DAT, 0x100);
1233 WRITE_VREG(MC_MPORT_CTRL, 0);
1234
1235 WRITE_VREG(MB_WIDTH, 0xff); /* invalid mb_width */
1236
1237 /* set slice start to 0x000000 or 0x000001 for check more_rbsp_data */
1238 WRITE_VREG(SLICE_START_BYTE_01, 0x00000000);
1239 WRITE_VREG(SLICE_START_BYTE_23, 0x01010000);
1240 /* set to mpeg2 to enable mismatch logic */
1241 WRITE_VREG(MPEG1_2_REG, 1);
1242 /* disable COEF_GT_64 , error_m4_table and voff_rw_err */
1243 WRITE_VREG(VLD_ERROR_MASK, 0x1011);
1244
1245 /* Config MCPU Amrisc interrupt */
1246 WRITE_VREG(ASSIST_AMR1_INT0, 0x1); /* viu_vsync_int */
1247 WRITE_VREG(ASSIST_AMR1_INT1, 0x5); /* mbox_isr */
1248 WRITE_VREG(ASSIST_AMR1_INT2, 0x8); /* vld_isr */
1249 WRITE_VREG(ASSIST_AMR1_INT3, 0x15); /* vififo_empty */
1250 WRITE_VREG(ASSIST_AMR1_INT4, 0xd); /* rv_ai_mb_finished_int */
1251 WRITE_VREG(ASSIST_AMR1_INT7, 0x14); /* dcac_dma_done */
1252
1253 /* Config MCPU Amrisc interrupt */
1254 WRITE_VREG(ASSIST_AMR1_INT5, 0x9); /* MCPU interrupt */
1255 WRITE_VREG(ASSIST_AMR1_INT6, 0x17); /* CCPU interrupt */
1256
1257 WRITE_VREG(CPC_P, 0xc00); /* CCPU Code will start from 0xc00 */
1258 WRITE_VREG(CINT_VEC_BASE, (0xc20 >> 5));
1259#if 0
1260 WRITE_VREG(POWER_CTL_VLD,
1261 READ_VREG(POWER_CTL_VLD) | (0 << 10) |
1262 (1 << 9) | (1 << 6));
1263#else
1264 WRITE_VREG(POWER_CTL_VLD, ((1 << 10) | /* disable cabac_step_2 */
1265 (1 << 9) | /* viff_drop_flag_en */
1266 (1 << 6) /* h264_000003_en */
1267 )
1268 );
1269#endif
1270 WRITE_VREG(M4_CONTROL_REG, (1 << 13)); /* H264_DECODE_INFO - h264_en */
1271
1272 WRITE_VREG(CANVAS_START, CANVAS_INDEX_START);
1273#if 1
1274 /* Start Address of Workspace (UCODE, temp_data...) */
1275 WRITE_VREG(WORKSPACE_START,
1276 video_domain_addr(work_space_adr));
1277#else
1278 /* Start Address of Workspace (UCODE, temp_data...) */
1279 WRITE_VREG(WORKSPACE_START,
1280 0x05000000);
1281#endif
1282 /* Clear all sequence parameter set available */
1283 WRITE_VREG(SPS_STATUS, 0);
1284 /* Clear all picture parameter set available */
1285 WRITE_VREG(PPS_STATUS, 0);
1286 /* Set current microcode to NULL */
1287 WRITE_VREG(CURRENT_UCODE, 0xff);
1288 /* Set current SPS/PPS to NULL */
1289 WRITE_VREG(CURRENT_SPS_PPS, 0xffff);
1290 /* Set decode status to DECODE_START_HEADER */
1291 WRITE_VREG(DECODE_STATUS, 1);
1292}
1293
1294static void vh264mvc_prot_init(void)
1295{
1296 while (READ_VREG(DCAC_DMA_CTRL) & 0x8000)
1297 ;
1298 while (READ_VREG(LMEM_DMA_CTRL) & 0x8000)
1299 ; /* reg address is 0x350 */
1300 /* clear mailbox interrupt */
1301 WRITE_VREG(ASSIST_MBOX1_CLR_REG, 1);
1302
1303 /* enable mailbox interrupt */
1304 WRITE_VREG(ASSIST_MBOX1_MASK, 1);
1305
1306 /* disable PSCALE for hardware sharing */
1307 WRITE_VREG(PSCALE_CTRL, 0);
1308
1309 H264_DECODE_INIT();
1310
1311#if 1 /* /MESON_CPU_TYPE >= MESON_CPU_TYPE_MESON6 */
1312 WRITE_VREG(DOS_SW_RESET0, (1 << 11));
1313 WRITE_VREG(DOS_SW_RESET0, 0);
1314
1315 READ_VREG(DOS_SW_RESET0);
1316 READ_VREG(DOS_SW_RESET0);
1317 READ_VREG(DOS_SW_RESET0);
1318
1319#else
1320 WRITE_RESET_REG(RESET0_REGISTER, 0x80); /* RESET MCPU */
1321#endif
1322
1323 WRITE_VREG(MAILBOX_COMMAND, 0);
1324 WRITE_VREG(BUFFER_RECYCLE, 0);
1325 WRITE_VREG(DROP_CONTROL, 0);
1326 CLEAR_VREG_MASK(MDEC_PIC_DC_CTRL, 1 << 17);
1327#if 1 /* /MESON_CPU_TYPE >= MESON_CPU_TYPE_MESON8 */
1328 WRITE_VREG(MDEC_PIC_DC_THRESH, 0x404038aa);
1329#endif
1330}
1331
1332static int vh264mvc_local_init(void)
1333{
1334 int i, size, ret;
1335 display_buff_id = -1;
1336 display_view_id = -1;
1337 display_POC = -1;
1338 no_dropping_cnt = 0;
1339 init_drop_cnt = INIT_DROP_FRAME_CNT;
1340
1341 for (i = 0; i < INIT_DROP_FRAME_CNT; i++)
1342 init_drop_frame_id[i] = 0;
1343
1344#ifdef DEBUG_PTS
1345 pts_missed = 0;
1346 pts_hit = 0;
1347#endif
1348
1349#ifdef DEBUG_SKIP
1350 view_total = 0;
1351 view_dropped = 0;
1352#endif
1353
1354 /* vh264mvc_ratio = vh264mvc_amstream_dec_info.ratio; */
1355 vh264mvc_ratio = 0x100;
1356
1357 /* frame_width = vh264mvc_amstream_dec_info.width; */
1358 /* frame_height = vh264mvc_amstream_dec_info.height; */
1359 frame_dur = vh264mvc_amstream_dec_info.rate;
1360 if (frame_dur == 0)
1361 frame_dur = 96000 / 24;
1362
1363 pts_outside = ((unsigned long) vh264mvc_amstream_dec_info.param) & 0x01;
1364 sync_outside = ((unsigned long) vh264mvc_amstream_dec_info.param & 0x02)
1365 >> 1;
1366 INIT_WORK(&alloc_work, do_alloc_work);
1367
1368 max_dec_frame_buffering[0] = -1;
1369 max_dec_frame_buffering[1] = -1;
1370 fill_ptr = get_ptr = put_ptr = putting_ptr = 0;
1371 dirty_frame_num = 0;
1372 for (i = 0; i < DECODE_BUFFER_NUM_MAX; i++) {
1373 view0_vfbuf_use[i] = 0;
1374 view1_vfbuf_use[i] = 0;
1375 }
1376
1377 for (i = 0; i < VF_POOL_SIZE; i++) {
1378 vfpool_idx[i].display_pos = -1;
1379 vfpool_idx[i].view0_buf_id = DISPLAY_INVALID_POS;
1380 vfpool_idx[i].view1_buf_id = -1;
1381 vfpool_idx[i].view0_drop = 0;
1382 vfpool_idx[i].view1_drop = 0;
1383 vfpool_idx[i].used = 0;
1384 }
1385 for (i = 0; i < VF_POOL_SIZE; i++) {
1386 memset(&vfpool[i], 0, sizeof(struct vframe_s));
1387 vfpool[i].index = i;
1388 }
1389 init_vf_buf();
1390
1391 if (mm_blk_handle) {
1392 decoder_bmmu_box_free(mm_blk_handle);
1393 mm_blk_handle = NULL;
1394 }
1395
1396 mm_blk_handle = decoder_bmmu_box_alloc_box(
1397 DRIVER_NAME,
1398 0,
1399 TOTAL_BMMU_BUFF_NUM,
1400 4 + PAGE_SHIFT,
1401 CODEC_MM_FLAGS_CMA_CLEAR |
1402 CODEC_MM_FLAGS_FOR_VDECODER);
1403
1404 size = DECODER_WORK_SPACE_SIZE;
1405 ret = decoder_bmmu_box_alloc_buf_phy(mm_blk_handle, 0,
1406 size, DRIVER_NAME, &work_space_adr);
1407
1408 return ret;
1409}
1410
1411static s32 vh264mvc_init(void)
1412{
1413 int ret = -1;
1414 char *buf = vmalloc(0x1000 * 16);
1415
1416 if (buf == NULL)
1417 return -ENOMEM;
1418
1419 pr_info("\nvh264mvc_init\n");
1420 init_timer(&recycle_timer);
1421
1422 stat |= STAT_TIMER_INIT;
1423
1424 ret = vh264mvc_vdec_info_init();
1425 if (0 != ret) {
1426 vfree(buf);
1427 return -ret;
1428 }
1429
1430 ret = vh264mvc_local_init();
1431 if (ret < 0) {
1432 vfree(buf);
1433 return ret;
1434 }
1435
1436 amvdec_enable();
1437
1438 if (tee_enabled()) {
1439 ret = amvdec_loadmc_ex(VFORMAT_H264MVC, NULL, buf);
1440 if (ret != 0) {
1441 amvdec_disable();
1442 vfree(buf);
1443 pr_err("H264_MVC: the %s fw loading failed, err: %x\n",
1444 tee_enabled() ? "TEE" : "local", ret);
1445 return -1;
1446 }
1447 } else {
1448 /* -- ucode loading (amrisc and swap code) */
1449 mc_cpu_addr = dma_alloc_coherent(amports_get_dma_device(),
1450 MC_TOTAL_SIZE, &mc_dma_handle, GFP_KERNEL);
1451 if (!mc_cpu_addr) {
1452 amvdec_disable();
1453 vfree(buf);
1454 pr_err("vh264_mvc init: Can not allocate mc memory.\n");
1455 return -ENOMEM;
1456 }
1457
1458 WRITE_VREG(UCODE_START_ADDR, mc_dma_handle);
1459
1460 if (get_firmware_data(VIDEO_DEC_H264_MVC, buf) < 0) {
1461 pr_err("get firmware fail.");
1462 vfree(buf);
1463 return -1;
1464 }
1465
1466 ret = amvdec_loadmc_ex(VFORMAT_H264MVC, NULL, buf);
1467
1468 /*header*/
1469 memcpy((u8 *) mc_cpu_addr, buf + 0x1000, 0x1000);
1470 /*mmco*/
1471 memcpy((u8 *) mc_cpu_addr + 0x1000, buf + 0x2000, 0x2000);
1472 /*slice*/
1473 memcpy((u8 *) mc_cpu_addr + 0x3000, buf + 0x4000, 0x3000);
1474
1475 if (ret < 0) {
1476 amvdec_disable();
1477
1478 dma_free_coherent(amports_get_dma_device(),
1479 MC_TOTAL_SIZE,
1480 mc_cpu_addr, mc_dma_handle);
1481 mc_cpu_addr = NULL;
1482 return -EBUSY;
1483 }
1484 }
1485 vfree(buf);
1486
1487 stat |= STAT_MC_LOAD;
1488
1489 /* enable AMRISC side protocol */
1490 vh264mvc_prot_init();
1491
1492#ifdef HANDLE_h264mvc_IRQ
1493 if (vdec_request_irq(VDEC_IRQ_1, vh264mvc_isr,
1494 "vh264mvc-irq", (void *)vh264mvc_dec_id)) {
1495 pr_info("vh264mvc irq register error.\n");
1496 amvdec_disable();
1497 return -ENOENT;
1498 }
1499#endif
1500
1501 stat |= STAT_ISR_REG;
1502
1503 vf_provider_init(&vh264mvc_vf_prov, PROVIDER_NAME,
1504 &vh264mvc_vf_provider, NULL);
1505 vf_reg_provider(&vh264mvc_vf_prov);
1506 vf_notify_receiver(PROVIDER_NAME, VFRAME_EVENT_PROVIDER_START, NULL);
1507
1508 stat |= STAT_VF_HOOK;
1509
1510 recycle_timer.data = (ulong) (&recycle_timer);
1511 recycle_timer.function = vh264mvc_put_timer_func;
1512 recycle_timer.expires = jiffies + PUT_INTERVAL;
1513
1514 add_timer(&recycle_timer);
1515
1516 stat |= STAT_TIMER_ARM;
1517
1518 amvdec_start();
1519
1520 stat |= STAT_VDEC_RUN;
1521
1522 return 0;
1523}
1524
1525static int vh264mvc_stop(void)
1526{
1527 if (stat & STAT_VDEC_RUN) {
1528 amvdec_stop();
1529 stat &= ~STAT_VDEC_RUN;
1530 }
1531
1532 if (stat & STAT_ISR_REG) {
1533 WRITE_VREG(ASSIST_MBOX1_MASK, 0);
1534#ifdef HANDLE_h264mvc_IRQ
1535 vdec_free_irq(VDEC_IRQ_1, (void *)vh264mvc_dec_id);
1536#endif
1537 stat &= ~STAT_ISR_REG;
1538 }
1539
1540 if (stat & STAT_TIMER_ARM) {
1541 del_timer_sync(&recycle_timer);
1542 stat &= ~STAT_TIMER_ARM;
1543 }
1544
1545 if (stat & STAT_VF_HOOK) {
1546 ulong flags;
1547
1548 spin_lock_irqsave(&lock, flags);
1549 spin_unlock_irqrestore(&lock, flags);
1550 vf_unreg_provider(&vh264mvc_vf_prov);
1551 stat &= ~STAT_VF_HOOK;
1552 }
1553
1554 if (stat & STAT_MC_LOAD) {
1555 if (mc_cpu_addr != NULL) {
1556 dma_free_coherent(amports_get_dma_device(),
1557 MC_TOTAL_SIZE, mc_cpu_addr, mc_dma_handle);
1558 mc_cpu_addr = NULL;
1559 }
1560
1561 stat &= ~STAT_MC_LOAD;
1562 }
1563
1564 amvdec_disable();
1565
1566 if (mm_blk_handle) {
1567 decoder_bmmu_box_free(mm_blk_handle);
1568 mm_blk_handle = NULL;
1569 }
1570 uninit_vf_buf();
1571 return 0;
1572}
1573
1574static void error_do_work(struct work_struct *work)
1575{
1576 if (atomic_read(&vh264mvc_active)) {
1577 vh264mvc_stop();
1578 vh264mvc_init();
1579 }
1580}
1581
1582static int amvdec_h264mvc_probe(struct platform_device *pdev)
1583{
1584 struct vdec_s *pdata = *(struct vdec_s **)pdev->dev.platform_data;
1585
1586 pr_info("amvdec_h264mvc probe start.\n");
1587 mutex_lock(&vh264_mvc_mutex);
1588
1589#if 0
1590 mem = platform_get_resource(pdev, IORESOURCE_MEM, 0);
1591 if (!mem) {
1592 pr_info("\namvdec_h264mvc memory resource undefined.\n");
1593 return -EFAULT;
1594 }
1595#endif
1596
1597 if (pdata == NULL) {
1598 mutex_unlock(&vh264_mvc_mutex);
1599 pr_info("\namvdec_h264mvc memory resource undefined.\n");
1600 return -EFAULT;
1601 }
1602
1603 if (pdata->sys_info)
1604 vh264mvc_amstream_dec_info = *pdata->sys_info;
1605
1606 pdata->dec_status = vh264mvc_dec_status;
1607 /* pdata->set_trickmode = vh264mvc_set_trickmode; */
1608
1609 if (vh264mvc_init() < 0) {
1610 pr_info("\namvdec_h264mvc init failed.\n");
1611 kfree(gvs);
1612 gvs = NULL;
1613 mutex_unlock(&vh264_mvc_mutex);
1614 return -ENODEV;
1615 }
1616
1617 INIT_WORK(&error_wd_work, error_do_work);
1618 INIT_WORK(&set_clk_work, vh264_mvc_set_clk);
1619
1620 atomic_set(&vh264mvc_active, 1);
1621
1622 mutex_unlock(&vh264_mvc_mutex);
1623
1624 pr_info("amvdec_h264mvc probe end.\n");
1625
1626 return 0;
1627}
1628
1629static int amvdec_h264mvc_remove(struct platform_device *pdev)
1630{
1631 pr_info("amvdec_h264mvc_remove\n");
1632 cancel_work_sync(&alloc_work);
1633 cancel_work_sync(&error_wd_work);
1634 cancel_work_sync(&set_clk_work);
1635 vh264mvc_stop();
1636 frame_width = 0;
1637 frame_height = 0;
1638 vdec_source_changed(VFORMAT_H264MVC, 0, 0, 0);
1639 atomic_set(&vh264mvc_active, 0);
1640
1641#ifdef DEBUG_PTS
1642 pr_info
1643 ("pts missed %ld, pts hit %ld, pts_outside %d, ",
1644 pts_missed, pts_hit, pts_outside);
1645 pr_info("duration %d, sync_outside %d\n",
1646 frame_dur, sync_outside);
1647#endif
1648
1649#ifdef DEBUG_SKIP
1650 pr_info("view_total = %ld, dropped %ld\n", view_total, view_dropped);
1651#endif
1652 kfree(gvs);
1653 gvs = NULL;
1654
1655 return 0;
1656}
1657
1658/****************************************/
1659#ifdef CONFIG_PM
1660static int h264mvc_suspend(struct device *dev)
1661{
1662 amvdec_suspend(to_platform_device(dev), dev->power.power_state);
1663 return 0;
1664}
1665
1666static int h264mvc_resume(struct device *dev)
1667{
1668 amvdec_resume(to_platform_device(dev));
1669 return 0;
1670}
1671
1672static const struct dev_pm_ops h264mvc_pm_ops = {
1673 SET_SYSTEM_SLEEP_PM_OPS(h264mvc_suspend, h264mvc_resume)
1674};
1675#endif
1676
1677static struct platform_driver amvdec_h264mvc_driver = {
1678 .probe = amvdec_h264mvc_probe,
1679 .remove = amvdec_h264mvc_remove,
1680 .driver = {
1681 .name = DRIVER_NAME,
1682#ifdef CONFIG_PM
1683 .pm = &h264mvc_pm_ops,
1684#endif
1685 }
1686};
1687
1688static struct codec_profile_t amvdec_hmvc_profile = {
1689 .name = "hmvc",
1690 .profile = ""
1691};
1692static struct codec_profile_t amvdec_hmvc_profile_single;
1693
1694static struct mconfig h264mvc_configs[] = {
1695 MC_PU32("stat", &stat),
1696 MC_PU32("dbg_mode", &dbg_mode),
1697 MC_PU32("view_mode", &view_mode),
1698 MC_PU32("dbg_cmd", &dbg_cmd),
1699 MC_PU32("drop_rate", &drop_rate),
1700 MC_PU32("drop_thread_hold", &drop_thread_hold),
1701};
1702static struct mconfig_node h264mvc_node;
1703
1704static int __init amvdec_h264mvc_driver_init_module(void)
1705{
1706 pr_debug("amvdec_h264mvc module init\n");
1707
1708 if (platform_driver_register(&amvdec_h264mvc_driver)) {
1709 pr_err("failed to register amvdec_h264mvc driver\n");
1710 return -ENODEV;
1711 }
1712
1713 vcodec_profile_register(&amvdec_hmvc_profile);
1714 amvdec_hmvc_profile_single = amvdec_hmvc_profile;
1715 amvdec_hmvc_profile_single.name = "h264mvc";
1716 vcodec_profile_register(&amvdec_hmvc_profile_single);
1717 INIT_REG_NODE_CONFIGS("media.decoder", &h264mvc_node,
1718 "h264mvc", h264mvc_configs, CONFIG_FOR_RW);
1719 return 0;
1720}
1721
1722static void __exit amvdec_h264mvc_driver_remove_module(void)
1723{
1724 pr_debug("amvdec_h264mvc module remove.\n");
1725
1726 platform_driver_unregister(&amvdec_h264mvc_driver);
1727}
1728
1729/****************************************/
1730
1731module_param(stat, uint, 0664);
1732MODULE_PARM_DESC(stat, "\n amvdec_h264mvc stat\n");
1733
1734module_param(dbg_mode, uint, 0664);
1735MODULE_PARM_DESC(dbg_mode, "\n amvdec_h264mvc dbg mode\n");
1736
1737module_param(view_mode, uint, 0664);
1738MODULE_PARM_DESC(view_mode, "\n amvdec_h264mvc view mode\n");
1739
1740module_param(dbg_cmd, uint, 0664);
1741MODULE_PARM_DESC(dbg_cmd, "\n amvdec_h264mvc cmd mode\n");
1742
1743module_param(drop_rate, uint, 0664);
1744MODULE_PARM_DESC(drop_rate, "\n amvdec_h264mvc drop rate\n");
1745
1746module_param(drop_thread_hold, uint, 0664);
1747MODULE_PARM_DESC(drop_thread_hold, "\n amvdec_h264mvc drop thread hold\n");
1748module_init(amvdec_h264mvc_driver_init_module);
1749module_exit(amvdec_h264mvc_driver_remove_module);
1750
1751MODULE_DESCRIPTION("AMLOGIC h264mvc Video Decoder Driver");
1752MODULE_LICENSE("GPL");
1753MODULE_AUTHOR("Chen Zhang <chen.zhang@amlogic.com>");
1754