blob: 8f8c39c95cfe341f5269b8f2e994674fa99d1e6e [file] [log] [blame]
xjb04a4022021-11-25 15:01:52 +08001/* Copyright Statement:
2 *
3 * This software/firmware and related documentation ("MediaTek Software") are
4 * protected under relevant copyright laws. The information contained herein
5 * is confidential and proprietary to MediaTek Inc. and/or its licensors.
6 * Without the prior written permission of MediaTek inc. and/or its licensors,
7 * any reproduction, modification, use or disclosure of MediaTek Software,
8 * and information contained herein, in whole or in part, shall be strictly
9 * prohibited.
10 */
11/* MediaTek Inc. (C) 2019. All rights reserved.
12 *
13 * BY OPENING THIS FILE, RECEIVER HEREBY UNEQUIVOCALLY ACKNOWLEDGES AND AGREES
14 * THAT THE SOFTWARE/FIRMWARE AND ITS DOCUMENTATIONS ("MEDIATEK SOFTWARE")
15 * RECEIVED FROM MEDIATEK AND/OR ITS REPRESENTATIVES ARE PROVIDED TO RECEIVER ON
16 * AN "AS-IS" BASIS ONLY. MEDIATEK EXPRESSLY DISCLAIMS ANY AND ALL WARRANTIES,
17 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES OF
18 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE OR NONINFRINGEMENT.
19 * NEITHER DOES MEDIATEK PROVIDE ANY WARRANTY WHATSOEVER WITH RESPECT TO THE
20 * SOFTWARE OF ANY THIRD PARTY WHICH MAY BE USED BY, INCORPORATED IN, OR
21 * SUPPLIED WITH THE MEDIATEK SOFTWARE, AND RECEIVER AGREES TO LOOK ONLY TO SUCH
22 * THIRD PARTY FOR ANY WARRANTY CLAIM RELATING THERETO. RECEIVER EXPRESSLY
23 * ACKNOWLEDGES THAT IT IS RECEIVER\'S SOLE RESPONSIBILITY TO OBTAIN FROM ANY
24 * THIRD PARTY ALL PROPER LICENSES CONTAINED IN MEDIATEK SOFTWARE. MEDIATEK
25 * SHALL ALSO NOT BE RESPONSIBLE FOR ANY MEDIATEK SOFTWARE RELEASES MADE TO
26 * RECEIVER\'S SPECIFICATION OR TO CONFORM TO A PARTICULAR STANDARD OR OPEN
27 * FORUM. RECEIVER\'S SOLE AND EXCLUSIVE REMEDY AND MEDIATEK\'S ENTIRE AND
28 * CUMULATIVE LIABILITY WITH RESPECT TO THE MEDIATEK SOFTWARE RELEASED HEREUNDER
29 * WILL BE, AT MEDIATEK\'S OPTION, TO REVISE OR REPLACE THE MEDIATEK SOFTWARE
30 * AT ISSUE, OR REFUND ANY SOFTWARE LICENSE FEES OR SERVICE CHARGE PAID BY
31 * RECEIVER TO MEDIATEK FOR SUCH MEDIATEK SOFTWARE AT ISSUE.
32 *
33 * The following software/firmware and/or related documentation
34 * ("MediaTek Software") have been modified by MediaTek Inc. All revisions are
35 * subject to any receiver\'s applicable license agreements with MediaTek Inc.
36 */
37
38#include "scp_ipi.h"
39#include "encoding.h"
40
41
42static struct ipi_wrapper ipi_legacy_id [] = IPI_LEGACY_GROUP;
43ipi_handler_t mpool_handle_list[IPI_WRAPPER_TOTAL - IPI_MPOOL - 1];
44struct ipi_legacy_pkt {
45 unsigned int id;
46 unsigned int len;
47 void *data;
48};
49
50/*
51 * This is a handler for handling legacy ipi callback function
52 */
53static void legacy_handler(int id, void *prdata, void *data, unsigned int len)
54{
55 ipi_handler_t handler;
56 unsigned int ptr = (unsigned int)data;
57 struct ipi_legacy_pkt pkt;
58
59 /* variation length will only support chre, chrex and sensor for reducing
60 * slot and cpu time cost by memcpy.
61 */
62 pkt.id = *(unsigned int *)ptr;
63 pkt.len = *(unsigned int *)(ptr + 4);
64 pkt.data = (void *)(ptr + 8);
65
66 if (pkt.id > IPI_MPOOL)
67 handler = mpool_handle_list[pkt.id - IPI_MPOOL - 1];
68 else
69 handler = (ipi_handler_t)prdata;
70 handler(pkt.id, pkt.data, pkt.len);
71}
72
73/*
74 * Wrapper api for legacy api and supports only legacy features
75 * which is listed in ipi_legacy_id[]
76 */
77ipi_status scp_ipi_send(enum ipi_id id, void* buf, uint32_t len, uint32_t wait,
78 enum ipi_dir dir)
79{
80 int ret = 0, tmp_id;
81 void *ptr;
82
83 if (id >= IPI_WRAPPER_TOTAL || id == IPI_MPOOL) {
84 PRINTF_E("%s: id not support\n", __func__);
85 return ERROR;
86 }
87
88 if (id > IPI_MPOOL)
89 tmp_id = IPI_MPOOL;
90 else
91 tmp_id = id;
92
93 if (len > (ipi_legacy_id[tmp_id].out_size - 2) * MBOX_SLOT_SIZE) {
94 PRINTF_E("%s: len overflow\n", __func__);
95 return ERROR;
96 }
97
98 /* variation length will only support chre and sensor for reducing slot
99 * and cpu time cost by memcpy.
100 */
101 char pkt[ipi_legacy_id[tmp_id].out_size * MBOX_SLOT_SIZE];
102 memcpy((void *)pkt, (void *)&id, sizeof(uint32_t));
103 memcpy((void *)(pkt + 4), (void *)&len, sizeof(uint32_t));
104 memcpy((void *)(pkt + 8), buf, len);
105 ptr = pkt;
106
107 if (mrv_read_csr(CSR_MHARTID) == 0)
108 ret = ipi_send(ipi_legacy_id[tmp_id].out_id_0, ptr,
109 (int)ipi_legacy_id[tmp_id].out_size,
110 wait * IPI_WAIT_LEGACY);
111 else
112 ret = ipi_send(ipi_legacy_id[tmp_id].out_id_1, ptr,
113 (int)ipi_legacy_id[tmp_id].out_size,
114 wait * IPI_WAIT_LEGACY);
115
116 if (ret == IPI_ACTION_DONE)
117 return DONE;
118 else if (ret == IPI_PIN_BUSY)
119 return BUSY;
120 else
121 return ERROR;
122}
123
124ipi_status scp_ipi_registration(enum ipi_id id, ipi_handler_t handler,
125 const char *name)
126{
127 int ret = 0;
128
129 if (id >= IPI_WRAPPER_TOTAL || id == IPI_MPOOL) {
130 PRINTF_E("%s: id not support\n", __func__);
131 return ERROR;
132 }
133
134 if (id > IPI_MPOOL) {
135 /* if there's any new ipi, hook handler only */
136 mpool_handle_list[id - IPI_MPOOL - 1] = handler;
137 return DONE;
138 }
139
140 if (mrv_read_csr(CSR_MHARTID) == 0) {
141 ret = ipi_register(ipi_legacy_id[id].in_id_0, legacy_handler,
142 handler, ipi_legacy_id[id].msg);
143 } else {
144 ret = ipi_register(ipi_legacy_id[id].in_id_1, legacy_handler,
145 handler, ipi_legacy_id[id].msg);
146 }
147
148 if (ret == IPI_ACTION_DONE)
149 return DONE;
150 else
151 return ERROR;
152}
153
154void scp_legacy_ipi_init(void)
155{
156 int ret = 0;
157
158 if (mrv_read_csr(CSR_MHARTID) == 0) {
159 ret = ipi_register(IPI_IN_SCP_MPOOL_0, legacy_handler, 0,
160 msg_legacy_ipi_mpool);
161 } else {
162 ret = ipi_register(IPI_IN_SCP_MPOOL_1, legacy_handler, 0,
163 msg_legacy_ipi_mpool);
164 }
165
166 if (ret)
167 PRINTF_E("ipi mpool register fail, ret %d\n", ret);
168}