1 /***************************************************************************//**
2 * \file cy_syspm_ppu.c
3 * \version 5.150
4 *
5 * This file provides the source code for ARM PPU Platform PD specific driver,
6 * where the API's are used by Syspm driver for Power Management.
7 *
8 *
9 ********************************************************************************
10 * \copyright
11 * Copyright 2016-2020 Cypress Semiconductor Corporation
12 * SPDX-License-Identifier: Apache-2.0
13 *
14 * Licensed under the Apache License, Version 2.0 (the "License");
15 * you may not use this file except in compliance with the License.
16 * You may obtain a copy of the License at
17 *
18 *     http://www.apache.org/licenses/LICENSE-2.0
19 *
20 * Unless required by applicable law or agreed to in writing, software
21 * distributed under the License is distributed on an "AS IS" BASIS,
22 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
23 * See the License for the specific language governing permissions and
24 * limitations under the License.
25 *******************************************************************************/
26 
27 #include "cy_device.h"
28 
29 #if defined (CY_IP_MXS28SRSS) || defined (CY_IP_MXS40SSRSS) || defined (CY_IP_MXS22SRSS)
30 
31 #include <stdbool.h>
32 #include <ppu_v1.h>
33 #include <cy_syspm_ppu.h>
34 #include "cy_syslib.h"
35 #include "cy_syspm.h"
36 #if defined (CY_IP_MXS22SRSS) && !defined (COMPONENT_SECURE_DEVICE)
37 #include "cy_secure_services.h"
38 #endif
39 /**
40 * \addtogroup group_syspm_ppu_functions
41 * \{
42 */
43 
44 /*******************************************************************************
45 * Function Name: cy_pd_ppu_init
46 ****************************************************************************//**
47 *
48 * Initializes the PD PPU Driver.
49 *
50 *  \param ppu
51 *  This parameter contains PPU base pointer for which the initialization has
52 *  to be done.
53 *
54 *  \return the PD PPU API status \ref cy_en_syspm_status_t.
55 *
56 *******************************************************************************/
cy_pd_ppu_init(struct ppu_v1_reg * ppu)57 cy_en_syspm_status_t cy_pd_ppu_init(struct ppu_v1_reg *ppu)
58 {
59     CY_ASSERT(ppu != NULL);
60 
61     ppu_v1_init(ppu);
62 
63     return CY_SYSPM_SUCCESS;
64 }
65 
66 /*******************************************************************************
67 * Function Name: cy_pd_ppu_get_programmed_power_mode
68 ****************************************************************************//**
69 *
70 * Gets the programmed power mode of the particular PPU.
71 *
72 *  \param ppu
73 *  This parameter contains PPU base pointer for which the initialization has
74 *  to be done.
75 *
76 *  \return Returns the PPU Programmed Power mode
77 *
78 *******************************************************************************/
79 
cy_pd_ppu_get_programmed_power_mode(struct ppu_v1_reg * ppu)80 enum ppu_v1_mode cy_pd_ppu_get_programmed_power_mode(struct ppu_v1_reg *ppu)
81 {
82     CY_ASSERT(ppu != NULL);
83 #if defined(NO_RPC_CALL) || !defined (CY_IP_MXS22SRSS) || (defined (COMPONENT_SECURE_DEVICE) && defined (CY_IP_MXS22SRSS))
84     return ppu_v1_get_programmed_power_mode(ppu);
85 #else
86     cy_rpc_args_t rpcArgs;
87     rpcArgs.argc = 1;
88     rpcArgs.argv[0] = (uint32_t)ppu;
89     return (enum ppu_v1_mode)Cy_Send_RPC(CY_SECURE_SERVICE_TYPE_PM,
90                   (uint32_t)CY_SECURE_SERVICE_PM_GET_PROGRAMMED_POWER_MODE, &rpcArgs);
91 #endif
92 }
93 
94 
95 /*******************************************************************************
96 * Function Name: cy_pd_ppu_get_power_mode
97 ****************************************************************************//**
98 *
99 * Gets the current power mode of the particular PPU.
100 *
101 *  \param ppu
102 *  This parameter contains PPU base pointer for which the initialization has
103 *  to be done.
104 *
105 *  \return Returns the PPU Current Power mode
106 *
107 *******************************************************************************/
108 
cy_pd_ppu_get_power_mode(struct ppu_v1_reg * ppu)109 enum ppu_v1_mode cy_pd_ppu_get_power_mode(struct ppu_v1_reg *ppu)
110 {
111     CY_ASSERT(ppu != NULL);
112 #if defined(NO_RPC_CALL) || !defined (CY_IP_MXS22SRSS) || (defined (COMPONENT_SECURE_DEVICE) && defined (CY_IP_MXS22SRSS))
113     return ppu_v1_get_power_mode(ppu);
114 #else
115     cy_rpc_args_t rpcArgs;
116     rpcArgs.argc = 1;
117     rpcArgs.argv[0] = (uint32_t)ppu;
118     return (enum ppu_v1_mode)Cy_Send_RPC(CY_SECURE_SERVICE_TYPE_PM,
119                   (uint32_t)CY_SECURE_SERVICE_PM_GET_POWER_MODE, &rpcArgs);
120 #endif
121 }
122 
123 /*******************************************************************************
124 * Function Name: cy_pd_ppu_set_power_mode
125 ****************************************************************************//**
126 *
127 * Sets the required power mode of the particular PPU.
128 *
129 *  \param ppu
130 *  This parameter contains PPU base pointer for which the initialization has
131 *  to be done.
132 *
133 *  \param mode
134 *  Contains the future power mode to be set for the PPU.
135 *
136 *  \return the PD PPU API status \ref cy_en_syspm_status_t.
137 *
138 *******************************************************************************/
139 
cy_pd_ppu_set_power_mode(struct ppu_v1_reg * ppu,uint32_t mode)140 cy_en_syspm_status_t cy_pd_ppu_set_power_mode(struct ppu_v1_reg *ppu, uint32_t mode)
141 {
142 #if defined(NO_RPC_CALL) || !defined (CY_IP_MXS22SRSS) || (defined (COMPONENT_SECURE_DEVICE) && defined (CY_IP_MXS22SRSS))
143     cy_en_syspm_status_t status = CY_SYSPM_INVALID_STATE;
144     CY_ASSERT(ppu != NULL);
145     CY_ASSERT(mode < PPU_V1_MODE_COUNT);
146 
147     (void)ppu_v1_dynamic_enable(ppu, (enum ppu_v1_mode) mode); /* Suppress a compiler warning about unused return value */
148 
149     return status;
150 #else
151     cy_rpc_args_t rpcArgs;
152     rpcArgs.argc = 2;
153     rpcArgs.argv[0] = (uint32_t)ppu;
154     rpcArgs.argv[1] = mode;
155     return (cy_en_syspm_status_t)Cy_Send_RPC(CY_SECURE_SERVICE_TYPE_PM,
156               (uint32_t)CY_SECURE_SERVICE_PM_SET_POWER_MODE, &rpcArgs);
157 #endif
158 }
159 
160 /*******************************************************************************
161 * Function Name: cy_pd_ppu_enable_dynamic_mode
162 ****************************************************************************//**
163 *
164 * Enables/Disable Dynamic Mode of particular PPU.
165 *
166 *  \param ppu
167 *  This parameter contains PPU base pointer for which the initialization has
168 *  to be done.
169 *
170 *  \param enable
171 *  true  - Enables the Dynamic mode for the PD.
172 *  false - Disables the Dynamic mode for the PD.
173 *
174 *******************************************************************************/
175 
cy_pd_ppu_enable_dynamic_mode(struct ppu_v1_reg * ppu,bool enable)176 void cy_pd_ppu_enable_dynamic_mode(struct ppu_v1_reg *ppu, bool enable)
177 {
178     CY_ASSERT(ppu != NULL);
179 
180     if(enable)
181     {
182         ppu->PWPR |= PPU_V1_PWPR_DYNAMIC_EN;
183     }
184     else
185     {
186         ppu->PWPR &= ~(PPU_V1_PWPR_DYNAMIC_EN);
187     }
188 }
189 
190 /*******************************************************************************
191 * Function Name: cy_pd_ppu_set_static_power_mode
192 ****************************************************************************//**
193 *
194 * Sets the required static power mode of the particular PPU.
195 *
196 *  \param ppu
197 *  This parameter contains PPU base pointer for which the initialization has
198 *  to be done.
199 *
200 *  \param mode
201 *  Contains the future power mode to be set for the PPU.
202 *
203 *  \return the PD PPU API status \ref cy_en_syspm_status_t.
204 *
205 *******************************************************************************/
206 
cy_pd_ppu_set_static_power_mode(struct ppu_v1_reg * ppu,uint32_t mode)207 cy_en_syspm_status_t cy_pd_ppu_set_static_power_mode(struct ppu_v1_reg *ppu, uint32_t mode)
208 {
209 #if defined(NO_RPC_CALL) || !defined (CY_IP_MXS22SRSS) || (defined (COMPONENT_SECURE_DEVICE) && defined (CY_IP_MXS22SRSS))
210     cy_en_syspm_status_t status = CY_SYSPM_INVALID_STATE;
211     CY_ASSERT(ppu != NULL);
212     CY_ASSERT(mode < PPU_V1_MODE_COUNT);
213 
214     (void)ppu_v1_set_power_mode(ppu, (enum ppu_v1_mode) mode); /* Suppress a compiler warning about unused return value */
215 
216     return status;
217 #else
218     cy_rpc_args_t rpcArgs;
219     rpcArgs.argc = 2;
220     rpcArgs.argv[0] = (uint32_t)ppu;
221     rpcArgs.argv[1] = mode;
222     return (cy_en_syspm_status_t)Cy_Send_RPC(CY_SECURE_SERVICE_TYPE_PM,
223               (uint32_t)CY_SECURE_SERVICE_PM_SET_STATIC_POWER_MODE, &rpcArgs);
224 #endif
225 }
226 
227 
228 
229 /*******************************************************************************
230 * Function Name: cy_pd_ppu_reset
231 ****************************************************************************//**
232 *
233 * Resets the PD using PPU.
234 *
235 *  \param ppu
236 *  This parameter contains PPU base pointer for which the initialization has
237 *  to be done.
238 *
239 *  \return the PD PPU API status \ref cy_en_syspm_status_t.
240 *
241 *******************************************************************************/
242 
cy_pd_ppu_reset(struct ppu_v1_reg * ppu)243 cy_en_syspm_status_t cy_pd_ppu_reset(struct ppu_v1_reg *ppu)
244 {
245     cy_en_syspm_status_t status;
246     CY_ASSERT(ppu != NULL);
247 
248     status = cy_pd_ppu_set_power_mode(ppu, (uint32_t)PPU_V1_MODE_OFF);
249     if (status == CY_SYSPM_SUCCESS)
250     {
251         status = cy_pd_ppu_set_power_mode(ppu, (uint32_t)PPU_V1_MODE_ON);
252     }
253 
254     return status;
255 }
256 
257 /*******************************************************************************
258 * Function Name: cy_pd_ppu_get_ds_fail_device
259 ****************************************************************************//**
260 *
261 * Gets the PPU's device ID(s) which caused the Deepsleep Failure.
262 *
263 *  \param ppu
264 *  This parameter contains PPU base pointer for which the initialization has
265 *  to be done.
266 *
267 *  \return Returns the PPU's device ID which caused the Deepsleep Failure
268 *
269 *******************************************************************************/
cy_pd_ppu_get_ds_fail_device(struct ppu_v1_reg * ppu)270 cy_pd_ppu_device_status_t cy_pd_ppu_get_ds_fail_device(struct ppu_v1_reg *ppu)
271 {
272     CY_ASSERT(ppu != NULL);
273     return (cy_pd_ppu_device_status_t)ppu_v1_get_failure_device_id(ppu);
274 }
275 
276 /** \} group_syspm_ppu_functions */
277 
278 #endif /* CY_IP_MXS28SRSS,CY_IP_MXS40SSRSS */
279