2 * Copyright (c) 2015-2016 MediaTek Inc.
3 * Author: Houlong Wei <houlong.wei@mediatek.com>
4 * Ming Hsiu Tsai <minghsiu.tsai@mediatek.com>
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License version 2 as
8 * published by the Free Software Foundation.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
16 #include "mtk_mdp_core.h"
17 #include "mtk_mdp_vpu.h"
21 static inline struct mtk_mdp_ctx
*vpu_to_ctx(struct mtk_mdp_vpu
*vpu
)
23 return container_of(vpu
, struct mtk_mdp_ctx
, vpu
);
26 static void mtk_mdp_vpu_handle_init_ack(struct mdp_ipi_comm_ack
*msg
)
28 struct mtk_mdp_vpu
*vpu
= (struct mtk_mdp_vpu
*)
29 (unsigned long)msg
->ap_inst
;
31 /* mapping VPU address to kernel virtual address */
32 vpu
->vsi
= (struct mdp_process_vsi
*)
33 vpu_mapping_dm_addr(vpu
->pdev
, msg
->vpu_inst_addr
);
34 vpu
->inst_addr
= msg
->vpu_inst_addr
;
37 static void mtk_mdp_vpu_ipi_handler(void *data
, unsigned int len
, void *priv
)
39 unsigned int msg_id
= *(unsigned int *)data
;
40 struct mdp_ipi_comm_ack
*msg
= (struct mdp_ipi_comm_ack
*)data
;
41 struct mtk_mdp_vpu
*vpu
= (struct mtk_mdp_vpu
*)
42 (unsigned long)msg
->ap_inst
;
43 struct mtk_mdp_ctx
*ctx
;
45 vpu
->failure
= msg
->status
;
48 case VPU_MDP_INIT_ACK
:
49 mtk_mdp_vpu_handle_init_ack(data
);
51 case VPU_MDP_DEINIT_ACK
:
52 case VPU_MDP_PROCESS_ACK
:
55 ctx
= vpu_to_ctx(vpu
);
56 dev_err(&ctx
->mdp_dev
->pdev
->dev
,
57 "handle unknown ipi msg:0x%x\n",
62 ctx
= vpu_to_ctx(vpu
);
63 mtk_mdp_dbg(0, "[%d]:msg 0x%x, failure:%d", ctx
->id
,
64 msg_id
, vpu
->failure
);
68 int mtk_mdp_vpu_register(struct platform_device
*pdev
)
70 struct mtk_mdp_dev
*mdp
= platform_get_drvdata(pdev
);
73 err
= vpu_ipi_register(mdp
->vpu_dev
, IPI_MDP
,
74 mtk_mdp_vpu_ipi_handler
, "mdp_vpu", NULL
);
76 dev_err(&mdp
->pdev
->dev
,
77 "vpu_ipi_registration fail status=%d\n", err
);
82 static int mtk_mdp_vpu_send_msg(void *msg
, int len
, struct mtk_mdp_vpu
*vpu
,
85 struct mtk_mdp_ctx
*ctx
= vpu_to_ctx(vpu
);
89 mtk_mdp_dbg(1, "[%d]:vpu pdev is NULL", ctx
->id
);
93 mutex_lock(&ctx
->mdp_dev
->vpulock
);
94 err
= vpu_ipi_send(vpu
->pdev
, (enum ipi_id
)id
, msg
, len
);
96 dev_err(&ctx
->mdp_dev
->pdev
->dev
,
97 "vpu_ipi_send fail status %d\n", err
);
98 mutex_unlock(&ctx
->mdp_dev
->vpulock
);
103 static int mtk_mdp_vpu_send_ap_ipi(struct mtk_mdp_vpu
*vpu
, uint32_t msg_id
)
106 struct mdp_ipi_comm msg
;
109 msg
.ipi_id
= IPI_MDP
;
110 msg
.vpu_inst_addr
= vpu
->inst_addr
;
111 msg
.ap_inst
= (unsigned long)vpu
;
112 err
= mtk_mdp_vpu_send_msg((void *)&msg
, sizeof(msg
), vpu
, IPI_MDP
);
113 if (!err
&& vpu
->failure
)
119 int mtk_mdp_vpu_init(struct mtk_mdp_vpu
*vpu
)
122 struct mdp_ipi_init msg
;
123 struct mtk_mdp_ctx
*ctx
= vpu_to_ctx(vpu
);
125 vpu
->pdev
= ctx
->mdp_dev
->vpu_dev
;
127 msg
.msg_id
= AP_MDP_INIT
;
128 msg
.ipi_id
= IPI_MDP
;
129 msg
.ap_inst
= (unsigned long)vpu
;
130 err
= mtk_mdp_vpu_send_msg((void *)&msg
, sizeof(msg
), vpu
, IPI_MDP
);
131 if (!err
&& vpu
->failure
)
137 int mtk_mdp_vpu_deinit(struct mtk_mdp_vpu
*vpu
)
139 return mtk_mdp_vpu_send_ap_ipi(vpu
, AP_MDP_DEINIT
);
142 int mtk_mdp_vpu_process(struct mtk_mdp_vpu
*vpu
)
144 return mtk_mdp_vpu_send_ap_ipi(vpu
, AP_MDP_PROCESS
);