1 /*******************************************************************************
2 * File Name: cyhal_clock.c
3 *
4 * Description:
5 * Provides an implementation for high level interface for interacting with the
6 * Cypress Clocks. This is a wrapper around the lower level PDL API.
7 *
8 ********************************************************************************
9 * \copyright
10 * Copyright 2018-2022 Cypress Semiconductor Corporation (an Infineon company) or
11 * an affiliate of Cypress Semiconductor Corporation
12 *
13 * SPDX-License-Identifier: Apache-2.0
14 *
15 * Licensed under the Apache License, Version 2.0 (the "License");
16 * you may not use this file except in compliance with the License.
17 * You may obtain a copy of the License at
18 *
19 *     http://www.apache.org/licenses/LICENSE-2.0
20 *
21 * Unless required by applicable law or agreed to in writing, software
22 * distributed under the License is distributed on an "AS IS" BASIS,
23 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
24 * See the License for the specific language governing permissions and
25 * limitations under the License.
26 *******************************************************************************/
27 
28 #include <stdlib.h>
29 #include <string.h>
30 #include "cy_sysclk.h"
31 #include "cy_utils.h"
32 #include "cyhal_clock.h"
33 #include "cyhal_system.h"
34 #include "cyhal_utils.h"
35 #include "cyhal_hwmgr.h"
36 
37 #if (CYHAL_DRIVER_AVAILABLE_CLOCK)
38 
39 #if defined(__cplusplus)
40 extern "C"
41 {
42 #endif
43 
44 #define _CYHAL_CLOCK_FLL_LOCK_TIME (20000UL)
45 #define _CYHAL_CLOCK_PLL_LOCK_TIME (10000UL)
46 
47 #if defined(PERI_PCLK_GR_NUM_Pos)
48 #if !defined(COMPONENT_CAT1D)
49 #define _CYHAL_CLOCK_GET_PCLK_GR_NUM(block) ((en_clk_dst_t)(_CYHAL_PERIPHERAL_GROUP_GET_GROUP(block) << PERI_PCLK_GR_NUM_Pos))
50 #else
51 #define _CYHAL_CLOCK_GET_PCLK_GR_NUM(block) ((en_clk_dst_t)((_CYHAL_PERIPHERAL_CLOCK_GET_INSTANCE(block) << PERI_PCLK_INST_NUM_Pos) | (_CYHAL_PERIPHERAL_CLOCK_GET_GROUP(block) << PERI_PCLK_GR_NUM_Pos)))
52 #endif
53 #else
54 #define _CYHAL_CLOCK_GET_PCLK_GR_NUM(block) ((en_clk_dst_t)0) /* Value is not used for devices that don't have PCLK groups. */
55 #endif
56 
57 /* We can't use the PDL-defined CY_SRSS_PILO_PRESENT because on CAT1A devices it performs a struct lookup
58  * which won't work in preprocessor expressions */
59 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C) || defined(COMPONENT_CAT1D)
60     #define _CYHAL_SRSS_PILO_PRESENT (SRSS_PILO_PRESENT)
61 #elif defined(COMPONENT_CAT1B)
62     #define _CYHAL_SRSS_PILO_PRESENT (SRSS_S40S_PILO_PRESENT)
63 #endif
64 
65 /******************************************************************************
66  ****************************** Clock Resources *******************************
67  *****************************************************************************/
68 const cyhal_clock_tolerance_t CYHAL_CLOCK_TOLERANCE_0_P = {CYHAL_TOLERANCE_PERCENT, 0};
69 const cyhal_clock_tolerance_t CYHAL_CLOCK_TOLERANCE_1_P = {CYHAL_TOLERANCE_PERCENT, 1};
70 const cyhal_clock_tolerance_t CYHAL_CLOCK_TOLERANCE_5_P = {CYHAL_TOLERANCE_PERCENT, 5};
71 
72 #if !defined(COMPONENT_CAT1D)
73 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_IMO = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_IMO, 0 };
74 #endif
75 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_EXT = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_EXT, 0 };
76 #if (_CYHAL_SRSS_ILO_PRESENT)
77 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C)
78 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_ILO[_CYHAL_SRSS_NUM_ILO] = {
79     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_ILO, 0 },
80     #if (SRSS_HT_VARIANT > 0)
81     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_ILO, 1 },
82     #endif
83 };
84 #endif
85 #endif
86 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_LF = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_LF, 0 };
87 /* PUMP clock is only available on CAT1A (SRSS V1) and CAT1B devices */
88 #if PUMP_PRESENT
89 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_PUMP = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PUMP, 0 };
90 #endif /* PUMP_PRESENT */
91 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_BAK = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_BAK, 0 };
92 #if !defined(COMPONENT_CAT1D)
93 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_ALT_SYS_TICK = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_ALT_SYS_TICK, 0 };
94 #endif
95 
96 #if defined(COMPONENT_CAT1C)
97 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_MEM = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_MEM, 0 };
98 #endif
99 
100 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_PATHMUX[SRSS_NUM_CLKPATH] =
101 {
102     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 0 },
103 #if (SRSS_NUM_CLKPATH > 1)
104     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 1 },
105 #endif
106 #if (SRSS_NUM_CLKPATH > 2)
107     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 2 },
108 #endif
109 #if (SRSS_NUM_CLKPATH > 3)
110     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 3 },
111 #endif
112 #if (SRSS_NUM_CLKPATH > 4)
113     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 4 },
114 #endif
115 #if (SRSS_NUM_CLKPATH > 5)
116     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 5 },
117 #endif
118 #if (SRSS_NUM_CLKPATH > 6)
119     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 6 },
120 #endif
121 #if (SRSS_NUM_CLKPATH > 7)
122     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 7 },
123 #endif
124 #if (SRSS_NUM_CLKPATH > 8)
125     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 8 },
126 #endif
127 #if (SRSS_NUM_CLKPATH > 9)
128     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 9 },
129 #endif
130 #if (SRSS_NUM_CLKPATH > 10)
131     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 10 },
132 #endif
133 #if (SRSS_NUM_CLKPATH > 11)
134     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 11 },
135 #endif
136 #if (SRSS_NUM_CLKPATH > 12)
137     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 12 },
138 #endif
139 #if (SRSS_NUM_CLKPATH > 13)
140     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 13 },
141 #endif
142 #if (SRSS_NUM_CLKPATH > 14)
143     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 14 },
144 #endif
145 #if (SRSS_NUM_CLKPATH > 15)
146     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PATHMUX, 15 },
147 #endif
148 };
149 
150 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_HF[SRSS_NUM_HFROOT] =
151 {
152     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 0 },
153 #if (SRSS_NUM_HFROOT > 1)
154     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 1 },
155 #endif
156 #if (SRSS_NUM_HFROOT > 2)
157     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 2 },
158 #endif
159 #if (SRSS_NUM_HFROOT > 3)
160     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 3 },
161 #endif
162 #if (SRSS_NUM_HFROOT > 4)
163     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 4 },
164 #endif
165 #if (SRSS_NUM_HFROOT > 5)
166     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 5 },
167 #endif
168 #if (SRSS_NUM_HFROOT > 6)
169     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 6 },
170 #endif
171 #if (SRSS_NUM_HFROOT > 7)
172     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 7 },
173 #endif
174 #if (SRSS_NUM_HFROOT > 8)
175     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 8 },
176 #endif
177 #if (SRSS_NUM_HFROOT > 9)
178     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 9 },
179 #endif
180 #if (SRSS_NUM_HFROOT > 10)
181     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 10 },
182 #endif
183 #if (SRSS_NUM_HFROOT > 11)
184     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 11 },
185 #endif
186 #if (SRSS_NUM_HFROOT > 12)
187     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 12 },
188 #endif
189 #if (SRSS_NUM_HFROOT > 13)
190     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 13 },
191 #endif
192 #if (SRSS_NUM_HFROOT > 14)
193     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 14 },
194 #endif
195 #if (SRSS_NUM_HFROOT > 15)
196     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_HF, 15 },
197 #endif
198 };
199 
200 #if SRSS_ECO_PRESENT
201 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_ECO = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_ECO, 0 };
202 #endif
203 #if SRSS_ALTHF_PRESENT
204 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_ALTHF = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_ALTHF, 0 };
205 #endif
206 #if SRSS_ALTLF_PRESENT
207 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_ALTLF = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_ALTLF, 0 };
208 #endif
209 #if _CYHAL_SRSS_PILO_PRESENT
210 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_PILO = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PILO, 0 };
211 #endif
212 #if SRSS_BACKUP_PRESENT || SRSS_WCO_PRESENT
213 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_WCO = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_WCO, 0 };
214 #endif
215 #if defined(COMPONENT_CAT1B) || (SRSS_MFO_PRESENT)
216 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_MFO = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_MFO, 0 };
217 #endif
218 #if defined(COMPONENT_CAT1B) || (SRSS_MFO_PRESENT) || defined(CY_IP_MXS22SRSS)
219 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_MF = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_MF, 0 };
220 #endif
221 
222 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C) || (SRSS_FLL_PRESENT)
223 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_FLL = { CYHAL_RSC_CLOCK, CYHAL_CLOCK_BLOCK_FLL, 0 };
224 #endif
225 
226 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C)
227 #if defined(COMPONENT_CAT1A)
228 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_FAST = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_FAST, 0 };
229 #else
230 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_FAST[_CYHAL_SRSS_NUM_FAST] =
231 {
232    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_FAST, 0 },
233    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_FAST, 1 },
234 };
235 #endif
236 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_SLOW = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_SLOW, 0 };
237 #endif
238 
239 
240 #if defined(CY_IP_MXPERI) && (CY_IP_MXPERI_VERSION < 3)
241 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_PERI = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 0 };
242 #endif
243 
244 #if (defined(CY_IP_MXPERI) && (CY_IP_MXPERI_VERSION >= 3)) || defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1D)
245 /* COMPONENT_CAT1C uses a hybrid approach from what was done on CAT1A and CAT1B. CAT1C devices support ClkPeri as well
246 as Peripheral Clock Groups. For CAT1C, ClkPeri is used to source everything in Peripheral Clock Group 0 (HF0) and other
247 Peripheral Clock Groups derive from one of the HFClks and have their own group divider. Thus we declare RSC_PERI Peri array for CAT1C */
248 
249 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_PERI[CY_PERI_GROUP_NR] =
250 {
251     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 0 },
252 #if (CY_PERI_GROUP_NR > 1)
253     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 1 },
254 #endif
255 #if (CY_PERI_GROUP_NR > 2)
256     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 2 },
257 #endif
258 #if (CY_PERI_GROUP_NR > 3)
259     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 3 },
260 #endif
261 #if (CY_PERI_GROUP_NR > 4)
262     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 4 },
263 #endif
264 #if (CY_PERI_GROUP_NR > 5)
265     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 5 },
266 #endif
267 #if (CY_PERI_GROUP_NR > 6)
268     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 6 },
269 #endif
270 #if (CY_PERI_GROUP_NR > 7)
271     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 7 },
272 #endif
273 #if (CY_PERI_GROUP_NR > 8)
274     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 8 },
275 #endif
276 #if (CY_PERI_GROUP_NR > 9)
277     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 9 },
278 #endif
279 #if (CY_PERI_GROUP_NR > 10)
280     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 10 },
281 #endif
282 #if (CY_PERI_GROUP_NR > 11)
283     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 11 },
284 #endif
285 #if (CY_PERI_GROUP_NR > 12)
286     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 12 },
287 #endif
288 #if (CY_PERI_GROUP_NR > 13)
289     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 13 },
290 #endif
291 #if (CY_PERI_GROUP_NR > 14)
292     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 14 },
293 #endif
294 #if (CY_PERI_GROUP_NR > 15)
295     { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PERI, 15 },
296 #endif
297 };
298 #endif
299 
300 
301 #if defined(COMPONENT_CAT1A) && !(defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0))
302 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_TIMER = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_TIMER, 0 };
303 #if (_CYHAL_SRSS_NUM_PLL > 0)
304 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_PLL[_CYHAL_SRSS_NUM_PLL] =
305 {
306    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL, 0 },
307 #if (_CYHAL_SRSS_NUM_PLL > 1)
308    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL, 1 },
309 #endif
310 #if (_CYHAL_SRSS_NUM_PLL > 2)
311    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL, 2 },
312 #endif
313 #if (_CYHAL_SRSS_NUM_PLL > 3)
314    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL, 3 },
315 #endif
316 #if (_CYHAL_SRSS_NUM_PLL > 4)
317    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL, 4 },
318 #endif
319 #if (_CYHAL_SRSS_NUM_PLL > 5)
320    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL, 5 },
321 #endif
322 #if (_CYHAL_SRSS_NUM_PLL > 6)
323    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL, 6 },
324 #endif
325 #if (_CYHAL_SRSS_NUM_PLL > 7)
326    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL, 7 },
327 #endif
328 #if (_CYHAL_SRSS_NUM_PLL > 8)
329    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL, 8 },
330 #endif
331 #if (_CYHAL_SRSS_NUM_PLL > 9)
332    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL, 9 },
333 #endif
334 #if (_CYHAL_SRSS_NUM_PLL > 10)
335    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL, 10 },
336 #endif
337 #if (_CYHAL_SRSS_NUM_PLL > 11)
338    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL, 11 },
339 #endif
340 #if (_CYHAL_SRSS_NUM_PLL > 12)
341    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL, 12 },
342 #endif
343 #if (_CYHAL_SRSS_NUM_PLL > 13)
344    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL, 13 },
345 #endif
346 #if (_CYHAL_SRSS_NUM_PLL > 14)
347    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL, 14 },
348 #endif
349 };
350 #endif
351 #endif
352 
353 #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1D) || (defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0))
354 #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1D)
355 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_IHO = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_IHO, 0 };
356 #if SRSS_ECO_PRESENT
357 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_ECO_PRESCALER = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_ECO_PRESCALER, 0 };
358 #endif
359 #if SRSS_BACKUP_S40E_LPECO_PRESENT
360 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_LPECO_PRESCALER = { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_LPECO_PRESCALER, 0 };
361 #endif
362 #endif
363 
364 #if (SRSS_NUM_PLL200M > 0)
365 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_PLL200M[SRSS_NUM_PLL200M] =
366 {
367    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL200, 0 },
368 #if (SRSS_NUM_PLL200M > 1)
369    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL200, 1 },
370 #endif
371 #if (SRSS_NUM_PLL200M > 2)
372    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL200, 2 },
373 #endif
374 #if (SRSS_NUM_PLL200M > 3)
375    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL200, 3 },
376 #endif
377 #if (SRSS_NUM_PLL200M > 4)
378    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL200, 4 },
379 #endif
380 #if (SRSS_NUM_PLL200M > 5)
381    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL200, 5 },
382 #endif
383 #if (SRSS_NUM_PLL200M > 6)
384    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL200, 6 },
385 #endif
386 #if (SRSS_NUM_PLL200M > 7)
387    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL200, 7 },
388 #endif
389 #if (SRSS_NUM_PLL200M > 8)
390    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL200, 8 },
391 #endif
392 #if (SRSS_NUM_PLL200M > 9)
393    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL200, 9 },
394 #endif
395 #if (SRSS_NUM_PLL200M > 10)
396    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL200, 10 },
397 #endif
398 #if (SRSS_NUM_PLL200M > 11)
399    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL200, 11 },
400 #endif
401 #if (SRSS_NUM_PLL200M > 12)
402    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL200, 12 },
403 #endif
404 #if (SRSS_NUM_PLL200M > 13)
405    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL200, 13 },
406 #endif
407 #if (SRSS_NUM_PLL200M > 14)
408    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL200, 14 },
409 #endif
410 };
411 #endif
412 
413 #if (SRSS_NUM_PLL400M > 0)
414 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_PLL400M[SRSS_NUM_PLL400M] =
415 {
416    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL400, 0 },
417 #if (SRSS_NUM_PLL400M > 1)
418    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL400, 1 },
419 #endif
420 #if (SRSS_NUM_PLL400M > 2)
421    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL400, 2 },
422 #endif
423 #if (SRSS_NUM_PLL400M > 3)
424    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL400, 3 },
425 #endif
426 #if (SRSS_NUM_PLL400M > 4)
427    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL400, 4 },
428 #endif
429 #if (SRSS_NUM_PLL400M > 5)
430    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL400, 5 },
431 #endif
432 #if (SRSS_NUM_PLL400M > 6)
433    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL400, 6 },
434 #endif
435 #if (SRSS_NUM_PLL400M > 7)
436    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL400, 7 },
437 #endif
438 #if (SRSS_NUM_PLL400M > 8)
439    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL400, 8 },
440 #endif
441 #if (SRSS_NUM_PLL400M > 9)
442    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL400, 9 },
443 #endif
444 #if (SRSS_NUM_PLL400M > 10)
445    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL400, 10 },
446 #endif
447 #if (SRSS_NUM_PLL400M > 11)
448    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL400, 11 },
449 #endif
450 #if (SRSS_NUM_PLL400M > 12)
451    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL400, 12 },
452 #endif
453 #if (SRSS_NUM_PLL400M > 13)
454    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL400, 13 },
455 #endif
456 #if (SRSS_NUM_PLL400M > 14)
457    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_PLL400, 14 },
458 #endif
459 };
460 #endif
461 
462 #if (SRSS_NUM_DPLL250M > 0)
463 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_DPLL250M[SRSS_NUM_DPLL250M] =
464 {
465    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL250, 0 },
466 #if (SRSS_NUM_DPLL250M > 1)
467    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL250, 1 },
468 #endif
469 #if (SRSS_NUM_DPLL250M > 2)
470    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL250, 2 },
471 #endif
472 #if (SRSS_NUM_DPLL250M > 3)
473    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL250, 3 },
474 #endif
475 #if (SRSS_NUM_DPLL250M > 4)
476    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL250, 4 },
477 #endif
478 #if (SRSS_NUM_DPLL250M > 5)
479    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL250, 5 },
480 #endif
481 #if (SRSS_NUM_DPLL250M > 6)
482    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL250, 6 },
483 #endif
484 #if (SRSS_NUM_DPLL250M > 7)
485    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL250, 7 },
486 #endif
487 #if (SRSS_NUM_DPLL250M > 8)
488    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL250, 8 },
489 #endif
490 #if (SRSS_NUM_DPLL250M > 9)
491    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL250, 9 },
492 #endif
493 #if (SRSS_NUM_DPLL250M > 10)
494    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL250, 10 },
495 #endif
496 #if (SRSS_NUM_DPLL250M > 11)
497    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL250, 11 },
498 #endif
499 #if (SRSS_NUM_DPLL250M > 12)
500    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL250, 12 },
501 #endif
502 #if (SRSS_NUM_DPLL250M > 13)
503    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL250, 13 },
504 #endif
505 #if (SRSS_NUM_DPLL250M > 14)
506    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL250, 14 },
507 #endif
508 };
509 #endif
510 
511 #if (SRSS_NUM_DPLL500M > 0)
512 const cyhal_resource_inst_t CYHAL_CLOCK_RSC_DPLL500M[SRSS_NUM_DPLL500M] =
513 {
514    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL500, 0 },
515 #if (SRSS_NUM_DPLL500M > 1)
516    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL500, 1 },
517 #endif
518 #if (SRSS_NUM_DPLL500M > 2)
519    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL500, 2 },
520 #endif
521 #if (SRSS_NUM_DPLL500M > 3)
522    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL500, 3 },
523 #endif
524 #if (SRSS_NUM_DPLL500M > 4)
525    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL500, 4 },
526 #endif
527 #if (SRSS_NUM_DPLL500M > 5)
528    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL500, 5 },
529 #endif
530 #if (SRSS_NUM_DPLL500M > 6)
531    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL500, 6 },
532 #endif
533 #if (SRSS_NUM_DPLL500M > 7)
534    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL500, 7 },
535 #endif
536 #if (SRSS_NUM_DPLL500M > 8)
537    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL500, 8 },
538 #endif
539 #if (SRSS_NUM_DPLL500M > 9)
540    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL500, 9 },
541 #endif
542 #if (SRSS_NUM_DPLL500M > 10)
543    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL500, 10 },
544 #endif
545 #if (SRSS_NUM_DPLL500M > 11)
546    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL500, 11 },
547 #endif
548 #if (SRSS_NUM_DPLL500M > 12)
549    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL500, 12 },
550 #endif
551 #if (SRSS_NUM_DPLL500M > 13)
552    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL500, 13 },
553 #endif
554 #if (SRSS_NUM_DPLL500M > 14)
555    { CYHAL_RSC_CLOCK, (uint8_t)CYHAL_CLOCK_BLOCK_DPLL500, 14 },
556 #endif
557 };
558 #endif
559 
560 #if ((SRSS_NUM_PLL400M > 0) && (SRSS_NUM_PLL200M == 0))
561 #define CYHAL_CLOCK_RSC_PLL CYHAL_CLOCK_RSC_PLL400M
562 #elif ((SRSS_NUM_PLL400M == 0) && (SRSS_NUM_PLL200M > 0))
563 #define CYHAL_CLOCK_RSC_PLL CYHAL_CLOCK_RSC_PLL200M
564 #endif
565 #endif
566 
567 /* HFCLK index that drives the current CPU core */
568 #if (CY_CPU_CORTEX_M7)
569 #define _CYHAL_CLOCK_CPU_HFCLK_IDX (1u)
570 #else
571 #define _CYHAL_CLOCK_CPU_HFCLK_IDX (0u)
572 #endif
573 
574 
575 /******************************************************************************
576  ***************************** Support Functions*******************************
577  *****************************************************************************/
578 
_cyhal_clock_compute_div(uint64_t input_hz,uint32_t desired_hz,uint32_t divider_bits,const cyhal_clock_tolerance_t * tolerance,uint32_t * div)579 static cy_rslt_t _cyhal_clock_compute_div(uint64_t input_hz, uint32_t desired_hz, uint32_t divider_bits, const cyhal_clock_tolerance_t *tolerance, uint32_t *div)
580 {
581     uint32_t max_div = (1 << divider_bits);
582     *div = (input_hz + (desired_hz / 2)) / desired_hz;
583     if (*div > max_div)
584         *div = max_div;
585 
586     uint32_t diff = (tolerance != NULL)
587         ? (uint32_t)abs(_cyhal_utils_calculate_tolerance(tolerance->type, desired_hz, input_hz / *div))
588         : 0;
589 
590     return ((tolerance != NULL) && (diff > tolerance->value))
591         ? CYHAL_CLOCK_RSLT_ERR_FREQ
592         : CY_RSLT_SUCCESS;
593 }
594 
_cyhal_clock_get_lf_frequency(void)595 static uint32_t _cyhal_clock_get_lf_frequency(void)
596 {
597     cy_en_clklf_in_sources_t source = Cy_SysClk_ClkLfGetSource();
598     switch (source)
599     {
600         case CY_SYSCLK_CLKLF_IN_ILO:
601 #if defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0)
602         case CY_SYSCLK_CLKLF_IN_ILO1:
603 #endif
604             return CY_SYSCLK_ILO_FREQ;
605 #if _CYHAL_SRSS_PILO_PRESENT
606         case CY_SYSCLK_CLKLF_IN_PILO:
607             return CY_SYSCLK_PILO_FREQ;
608 #endif
609 #if SRSS_BACKUP_PRESENT || SRSS_WCO_PRESENT
610         case CY_SYSCLK_CLKLF_IN_WCO:
611             return CY_SYSCLK_WCO_FREQ;
612 #endif
613 #if SRSS_ALTLF_PRESENT
614         case CY_SYSCLK_CLKLF_IN_ALTLF:
615             return Cy_SysClk_AltLfGetFrequency();
616 #endif
617 #if defined(COMPONENT_CAT1B)
618 #if SRSS_ECO_PRESENT
619         case CY_SYSCLK_CLKLF_IN_ECO_PRESCALER:
620             //return Cy_SysClk_EcoPrescalerGetFrequency();
621             return 0;
622 #endif
623 #if SRSS_BACKUP_S40E_LPECO_PRESENT
624         case CY_SYSCLK_CLKLF_IN_LPECO_PRESCALER:
625             return Cy_SysClk_LpEcoPrescalerGetFrequency();
626 #endif
627 #endif
628         default:
629             CY_ASSERT(false);
630             return 0;
631     }
632 }
633 
_cyhal_clock_update_system_state(bool before_change,uint32_t old_sysclk_freq_hz,uint32_t new_sysclk_freq_hz)634 static void _cyhal_clock_update_system_state(bool before_change, uint32_t old_sysclk_freq_hz, uint32_t new_sysclk_freq_hz)
635 {
636     // If increasing the clock frequency we need to update the speeds
637     // before the change. If decreasing the frequency we need to update
638     // after the change.
639     if ((before_change == (bool)(new_sysclk_freq_hz > old_sysclk_freq_hz)) ||
640         (!before_change == (new_sysclk_freq_hz < old_sysclk_freq_hz)))
641     {
642 #if defined(COMPONENT_CAT1A)
643         #if ((defined(SRSS_ULP_VARIANT)) && (SRSS_ULP_VARIANT == 0u))
644         bool is_ulp = false;
645         #else /* ((defined(SRSS_ULP_VARIANT)) && (SRSS_ULP_VARIANT == 0u)) */
646         bool is_ulp = Cy_SysPm_IsSystemUlp();
647         #endif /* ((defined(SRSS_ULP_VARIANT)) && (SRSS_ULP_VARIANT == 0u)) */
648 #elif defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1D)
649         bool is_ulp = true;
650 #elif defined(COMPONENT_CAT1C)
651         bool is_ulp = false;
652 #endif
653         Cy_SysLib_SetWaitStates(is_ulp, new_sysclk_freq_hz / 1000000);
654     }
655 
656     // If after the change, update the clock
657     if (!before_change)
658         SystemCoreClockUpdate();
659 }
660 
661 
_cyhal_clock_set_enabled_unsupported(cyhal_clock_t * clock,bool enabled,bool wait_for_lock)662 static cy_rslt_t _cyhal_clock_set_enabled_unsupported(cyhal_clock_t *clock, bool enabled, bool wait_for_lock)
663 {
664     CY_UNUSED_PARAMETER(clock);
665     CY_UNUSED_PARAMETER(enabled);
666     CY_UNUSED_PARAMETER(wait_for_lock);
667     CY_ASSERT(false); // Unhandled clock
668     return CYHAL_CLOCK_RSLT_ERR_NOT_SUPPORTED;
669 }
_cyhal_clock_set_frequency_unsupported(cyhal_clock_t * clock,uint32_t hz,const cyhal_clock_tolerance_t * tolerance)670 static cy_rslt_t _cyhal_clock_set_frequency_unsupported(cyhal_clock_t *clock, uint32_t hz, const cyhal_clock_tolerance_t *tolerance)
671 {
672     CY_UNUSED_PARAMETER(clock);
673     CY_UNUSED_PARAMETER(hz);
674     CY_UNUSED_PARAMETER(tolerance);
675     CY_ASSERT(false); // Unhandled clock
676     return CYHAL_CLOCK_RSLT_ERR_NOT_SUPPORTED;
677 }
_cyhal_clock_set_divider_unsupported(cyhal_clock_t * clock,uint32_t divider)678 static cy_rslt_t _cyhal_clock_set_divider_unsupported(cyhal_clock_t *clock, uint32_t divider)
679 {
680     CY_UNUSED_PARAMETER(clock);
681     CY_UNUSED_PARAMETER(divider);
682     CY_ASSERT(false); // Unhandled clock
683     return CYHAL_CLOCK_RSLT_ERR_NOT_SUPPORTED;
684 }
_cyhal_clock_set_source_unsupported(cyhal_clock_t * clock,const cyhal_clock_t * source)685 static cy_rslt_t _cyhal_clock_set_source_unsupported(cyhal_clock_t *clock, const cyhal_clock_t *source)
686 {
687     CY_UNUSED_PARAMETER(clock);
688     CY_UNUSED_PARAMETER(source);
689     CY_ASSERT(false); // Unhandled clock
690     return CYHAL_CLOCK_RSLT_ERR_NOT_SUPPORTED;
691 }
_cyhal_clock_is_enabled_true(const cyhal_clock_t * clock)692 static bool _cyhal_clock_is_enabled_true(const cyhal_clock_t *clock)
693 {
694     CY_UNUSED_PARAMETER(clock);
695     return true;
696 }
_cyhal_clock_get_sources_none(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)697 static cy_rslt_t _cyhal_clock_get_sources_none(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
698 {
699     CY_UNUSED_PARAMETER(clock);
700     CY_UNUSED_PARAMETER(sources);
701     *count = 0;
702     return CY_RSLT_SUCCESS;
703 }
704 
705 
706 static const cyhal_resource_inst_t *_CYHAL_CLOCK_SOURCE_HF[] =
707 {
708 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C) || (SRSS_FLL_PRESENT)
709     &CYHAL_CLOCK_RSC_FLL,
710 #endif
711 #if defined(COMPONENT_CAT1A) && !(defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0))
712 #if (_CYHAL_SRSS_NUM_PLL > 0)
713     &CYHAL_CLOCK_RSC_PLL[0],
714 #endif
715 #if (_CYHAL_SRSS_NUM_PLL > 1)
716     &CYHAL_CLOCK_RSC_PLL[1],
717 #endif
718 #if (_CYHAL_SRSS_NUM_PLL > 2)
719     &CYHAL_CLOCK_RSC_PLL[2],
720 #endif
721 #if (_CYHAL_SRSS_NUM_PLL > 3)
722     &CYHAL_CLOCK_RSC_PLL[3],
723 #endif
724 #if (_CYHAL_SRSS_NUM_PLL > 4)
725     &CYHAL_CLOCK_RSC_PLL[4],
726 #endif
727 #if (_CYHAL_SRSS_NUM_PLL > 5)
728     &CYHAL_CLOCK_RSC_PLL[5],
729 #endif
730 #if (_CYHAL_SRSS_NUM_PLL > 6)
731     &CYHAL_CLOCK_RSC_PLL[6],
732 #endif
733 #if (_CYHAL_SRSS_NUM_PLL > 7)
734     &CYHAL_CLOCK_RSC_PLL[7],
735 #endif
736 #if (_CYHAL_SRSS_NUM_PLL > 8)
737     &CYHAL_CLOCK_RSC_PLL[8],
738 #endif
739 #if (_CYHAL_SRSS_NUM_PLL > 9)
740     &CYHAL_CLOCK_RSC_PLL[9],
741 #endif
742 #if (_CYHAL_SRSS_NUM_PLL > 10)
743     &CYHAL_CLOCK_RSC_PLL[10],
744 #endif
745 #if (_CYHAL_SRSS_NUM_PLL > 11)
746     &CYHAL_CLOCK_RSC_PLL[11],
747 #endif
748 #if (_CYHAL_SRSS_NUM_PLL > 12)
749     &CYHAL_CLOCK_RSC_PLL[12],
750 #endif
751 #if (_CYHAL_SRSS_NUM_PLL > 13)
752     &CYHAL_CLOCK_RSC_PLL[13],
753 #endif
754 #elif (defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0))
755 #if (SRSS_NUM_PLL200M > 0)
756     &CYHAL_CLOCK_RSC_PLL200M[0],
757 #endif
758 #if (SRSS_NUM_PLL200M > 1)
759     &CYHAL_CLOCK_RSC_PLL200M[1],
760 #endif
761 #if (SRSS_NUM_PLL200M > 2)
762     &CYHAL_CLOCK_RSC_PLL200M[2],
763 #endif
764 #if (SRSS_NUM_PLL200M > 3)
765     &CYHAL_CLOCK_RSC_PLL200M[3],
766 #endif
767 #if (SRSS_NUM_PLL200M > 4)
768     &CYHAL_CLOCK_RSC_PLL200M[4],
769 #endif
770 #if (SRSS_NUM_PLL200M > 5)
771     &CYHAL_CLOCK_RSC_PLL200M[5],
772 #endif
773 #if (SRSS_NUM_PLL200M > 6)
774     &CYHAL_CLOCK_RSC_PLL200M[6],
775 #endif
776 #if (SRSS_NUM_PLL200M > 7)
777     &CYHAL_CLOCK_RSC_PLL200M[7],
778 #endif
779 #if (SRSS_NUM_PLL200M > 8)
780     &CYHAL_CLOCK_RSC_PLL200M[8],
781 #endif
782 #if (SRSS_NUM_PLL200M > 9)
783     &CYHAL_CLOCK_RSC_PLL200M[9],
784 #endif
785 #if (SRSS_NUM_PLL200M > 10)
786     &CYHAL_CLOCK_RSC_PLL200M[10],
787 #endif
788 #if (SRSS_NUM_PLL200M > 11)
789     &CYHAL_CLOCK_RSC_PLL200M[11],
790 #endif
791 #if (SRSS_NUM_PLL200M > 12)
792     &CYHAL_CLOCK_RSC_PLL200M[12],
793 #endif
794 #if (SRSS_NUM_PLL200M > 13)
795     &CYHAL_CLOCK_RSC_PLL200M[13],
796 #endif
797 #if (SRSS_NUM_PLL200M > 14)
798     &CYHAL_CLOCK_RSC_PLL200M[14],
799 #endif
800 #if (SRSS_NUM_PLL200M > 15)
801     &CYHAL_CLOCK_RSC_PLL200M[15],
802 #endif
803 #if (SRSS_NUM_PLL400M > 0)
804     &CYHAL_CLOCK_RSC_PLL400M[0],
805 #endif
806 #if (SRSS_NUM_PLL400M > 1)
807     &CYHAL_CLOCK_RSC_PLL400M[1],
808 #endif
809 #if (SRSS_NUM_PLL400M > 2)
810     &CYHAL_CLOCK_RSC_PLL400M[2],
811 #endif
812 #if (SRSS_NUM_PLL400M > 3)
813     &CYHAL_CLOCK_RSC_PLL400M[3],
814 #endif
815 #if (SRSS_NUM_PLL400M > 4)
816     &CYHAL_CLOCK_RSC_PLL400M[4],
817 #endif
818 #if (SRSS_NUM_PLL400M > 5)
819     &CYHAL_CLOCK_RSC_PLL400M[5],
820 #endif
821 #if (SRSS_NUM_PLL400M > 6)
822     &CYHAL_CLOCK_RSC_PLL400M[6],
823 #endif
824 #if (SRSS_NUM_PLL400M > 7)
825     &CYHAL_CLOCK_RSC_PLL400M[7],
826 #endif
827 #if (SRSS_NUM_PLL400M > 8)
828     &CYHAL_CLOCK_RSC_PLL400M[8],
829 #endif
830 #if (SRSS_NUM_PLL400M > 9)
831     &CYHAL_CLOCK_RSC_PLL400M[9],
832 #endif
833 #if (SRSS_NUM_PLL400M > 10)
834     &CYHAL_CLOCK_RSC_PLL400M[10],
835 #endif
836 #if (SRSS_NUM_PLL400M > 11)
837     &CYHAL_CLOCK_RSC_PLL400M[11],
838 #endif
839 #if (SRSS_NUM_PLL400M > 12)
840     &CYHAL_CLOCK_RSC_PLL400M[12],
841 #endif
842 #if (SRSS_NUM_PLL400M > 13)
843     &CYHAL_CLOCK_RSC_PLL400M[13],
844 #endif
845 #if (SRSS_NUM_PLL400M > 14)
846     &CYHAL_CLOCK_RSC_PLL400M[14],
847 #endif
848 #if (SRSS_NUM_PLL400M > 15)
849     &CYHAL_CLOCK_RSC_PLL400M[15],
850 #endif
851 #elif defined(COMPONENT_CAT1D)
852 #if (SRSS_NUM_DPLL250M > 0)
853     &CYHAL_CLOCK_RSC_DPLL250M[0],
854 #endif
855 #if (SRSS_NUM_DPLL250M > 1)
856     &CYHAL_CLOCK_RSC_DPLL250M[1],
857 #endif
858 #if (SRSS_NUM_DPLL250M > 2)
859     &CYHAL_CLOCK_RSC_DPLL250M[2],
860 #endif
861 #if (SRSS_NUM_DPLL250M > 3)
862     &CYHAL_CLOCK_RSC_DPLL250M[3],
863 #endif
864 #if (SRSS_NUM_DPLL250M > 4)
865     &CYHAL_CLOCK_RSC_DPLL250M[4],
866 #endif
867 #if (SRSS_NUM_DPLL250M > 5)
868     &CYHAL_CLOCK_RSC_DPLL250M[5],
869 #endif
870 #if (SRSS_NUM_DPLL250M > 6)
871     &CYHAL_CLOCK_RSC_DPLL250M[6],
872 #endif
873 #if (SRSS_NUM_DPLL250M > 7)
874     &CYHAL_CLOCK_RSC_DPLL250M[7],
875 #endif
876 #if (SRSS_NUM_DPLL250M > 8)
877     &CYHAL_CLOCK_RSC_DPLL250M[8],
878 #endif
879 #if (SRSS_NUM_DPLL250M > 9)
880     &CYHAL_CLOCK_RSC_DPLL250M[9],
881 #endif
882 #if (SRSS_NUM_DPLL250M > 10)
883     &CYHAL_CLOCK_RSC_DPLL250M[10],
884 #endif
885 #if (SRSS_NUM_DPLL250M > 11)
886     &CYHAL_CLOCK_RSC_DPLL250M[11],
887 #endif
888 #if (SRSS_NUM_DPLL250M > 12)
889     &CYHAL_CLOCK_RSC_DPLL250M[12],
890 #endif
891 #if (SRSS_NUM_DPLL250M > 13)
892     &CYHAL_CLOCK_RSC_DPLL250M[13],
893 #endif
894 #if (SRSS_NUM_DPLL250M > 14)
895     &CYHAL_CLOCK_RSC_DPLL250M[14],
896 #endif
897 #if (SRSS_NUM_DPLL250M > 15)
898     &CYHAL_CLOCK_RSC_DPLL250M[15],
899 #endif
900 #if (SRSS_NUM_DPLL500M > 0)
901     &CYHAL_CLOCK_RSC_DPLL500M[0],
902 #endif
903 #if (SRSS_NUM_DPLL500M > 1)
904     &CYHAL_CLOCK_RSC_DPLL500M[1],
905 #endif
906 #if (SRSS_NUM_DPLL500M > 2)
907     &CYHAL_CLOCK_RSC_DPLL500M[2],
908 #endif
909 #if (SRSS_NUM_DPLL500M > 3)
910     &CYHAL_CLOCK_RSC_DPLL500M[3],
911 #endif
912 #if (SRSS_NUM_DPLL500M > 4)
913     &CYHAL_CLOCK_RSC_DPLL500M[4],
914 #endif
915 #if (SRSS_NUM_DPLL500M > 5)
916     &CYHAL_CLOCK_RSC_DPLL500M[5],
917 #endif
918 #if (SRSS_NUM_DPLL500M > 6)
919     &CYHAL_CLOCK_RSC_DPLL500M[6],
920 #endif
921 #if (SRSS_NUM_DPLL500M > 7)
922     &CYHAL_CLOCK_RSC_DPLL500M[7],
923 #endif
924 #if (SRSS_NUM_DPLL500M > 8)
925     &CYHAL_CLOCK_RSC_DPLL500M[8],
926 #endif
927 #if (SRSS_NUM_DPLL500M > 9)
928     &CYHAL_CLOCK_RSC_DPLL500M[9],
929 #endif
930 #if (SRSS_NUM_DPLL500M > 10)
931     &CYHAL_CLOCK_RSC_DPLL500M[10],
932 #endif
933 #if (SRSS_NUM_DPLL500M > 11)
934     &CYHAL_CLOCK_RSC_DPLL500M[11],
935 #endif
936 #if (SRSS_NUM_DPLL500M > 12)
937     &CYHAL_CLOCK_RSC_DPLL500M[12],
938 #endif
939 #if (SRSS_NUM_DPLL500M > 13)
940     &CYHAL_CLOCK_RSC_DPLL500M[13],
941 #endif
942 #if (SRSS_NUM_DPLL500M > 14)
943     &CYHAL_CLOCK_RSC_DPLL500M[14],
944 #endif
945 #if (SRSS_NUM_DPLL500M > 15)
946     &CYHAL_CLOCK_RSC_DPLL500M[15],
947 #endif
948 #endif
949     &CYHAL_CLOCK_RSC_PATHMUX[0],
950 #if (SRSS_NUM_CLKPATH > 1)
951     &CYHAL_CLOCK_RSC_PATHMUX[1],
952 #endif
953 #if (SRSS_NUM_CLKPATH > 2)
954     &CYHAL_CLOCK_RSC_PATHMUX[2],
955 #endif
956 #if (SRSS_NUM_CLKPATH > 3)
957     &CYHAL_CLOCK_RSC_PATHMUX[3],
958 #endif
959 #if (SRSS_NUM_CLKPATH > 4)
960     &CYHAL_CLOCK_RSC_PATHMUX[4],
961 #endif
962 #if (SRSS_NUM_CLKPATH > 5)
963     &CYHAL_CLOCK_RSC_PATHMUX[5],
964 #endif
965 #if (SRSS_NUM_CLKPATH > 6)
966     &CYHAL_CLOCK_RSC_PATHMUX[6],
967 #endif
968 #if (SRSS_NUM_CLKPATH > 7)
969     &CYHAL_CLOCK_RSC_PATHMUX[7],
970 #endif
971 #if (SRSS_NUM_CLKPATH > 8)
972     &CYHAL_CLOCK_RSC_PATHMUX[8],
973 #endif
974 #if (SRSS_NUM_CLKPATH > 9)
975     &CYHAL_CLOCK_RSC_PATHMUX[9],
976 #endif
977 #if (SRSS_NUM_CLKPATH > 10)
978     &CYHAL_CLOCK_RSC_PATHMUX[10],
979 #endif
980 #if (SRSS_NUM_CLKPATH > 11)
981     &CYHAL_CLOCK_RSC_PATHMUX[11],
982 #endif
983 #if (SRSS_NUM_CLKPATH > 12)
984     &CYHAL_CLOCK_RSC_PATHMUX[12],
985 #endif
986 #if (SRSS_NUM_CLKPATH > 13)
987     &CYHAL_CLOCK_RSC_PATHMUX[13],
988 #endif
989 #if (SRSS_NUM_CLKPATH > 14)
990     &CYHAL_CLOCK_RSC_PATHMUX[14],
991 #endif
992 #if (SRSS_NUM_CLKPATH > 15)
993     &CYHAL_CLOCK_RSC_PATHMUX[15],
994 #endif
995 };
996 
997 #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C) || defined(COMPONENT_CAT1D)
_cyhal_clock_get_sources_peri_peripheral(uint8_t idx,const cyhal_resource_inst_t ** sources[],uint32_t * count)998 static cy_rslt_t _cyhal_clock_get_sources_peri_peripheral(uint8_t idx, const cyhal_resource_inst_t **sources[], uint32_t *count)
999 {
1000     static const cyhal_resource_inst_t *_CYHAL_CLOCK_SOURCE_PERI[SRSS_NUM_HFROOT] =
1001     {
1002         &CYHAL_CLOCK_RSC_HF[0],
1003     #if (SRSS_NUM_HFROOT > 1)
1004         &CYHAL_CLOCK_RSC_HF[1],
1005     #endif
1006     #if (SRSS_NUM_HFROOT > 2)
1007         &CYHAL_CLOCK_RSC_HF[2],
1008     #endif
1009     #if (SRSS_NUM_HFROOT > 3)
1010         &CYHAL_CLOCK_RSC_HF[3],
1011     #endif
1012     #if (SRSS_NUM_HFROOT > 4)
1013         &CYHAL_CLOCK_RSC_HF[4],
1014     #endif
1015     #if (SRSS_NUM_HFROOT > 5)
1016         &CYHAL_CLOCK_RSC_HF[5],
1017     #endif
1018     #if (SRSS_NUM_HFROOT > 6)
1019         &CYHAL_CLOCK_RSC_HF[6],
1020     #endif
1021     #if (SRSS_NUM_HFROOT > 7)
1022         &CYHAL_CLOCK_RSC_HF[7],
1023     #endif
1024     #if (SRSS_NUM_HFROOT > 8)
1025         &CYHAL_CLOCK_RSC_HF[8],
1026     #endif
1027     #if (SRSS_NUM_HFROOT > 9)
1028         &CYHAL_CLOCK_RSC_HF[9],
1029     #endif
1030     #if (SRSS_NUM_HFROOT > 10)
1031         &CYHAL_CLOCK_RSC_HF[10],
1032     #endif
1033     #if (SRSS_NUM_HFROOT > 11)
1034         &CYHAL_CLOCK_RSC_HF[11],
1035     #endif
1036     #if (SRSS_NUM_HFROOT > 12)
1037         &CYHAL_CLOCK_RSC_HF[12],
1038     #endif
1039     #if (SRSS_NUM_HFROOT > 13)
1040         &CYHAL_CLOCK_RSC_HF[13],
1041     #endif
1042     #if (SRSS_NUM_HFROOT > 14)
1043         &CYHAL_CLOCK_RSC_HF[14],
1044     #endif
1045     #if (SRSS_NUM_HFROOT > 15)
1046         &CYHAL_CLOCK_RSC_HF[15],
1047     #endif
1048     };
1049 
1050     *sources = &(_CYHAL_CLOCK_SOURCE_PERI[idx]);
1051     *count = 1;
1052     return CY_RSLT_SUCCESS;
1053 }
1054 #endif
1055 
1056 
1057 // IMO
1058 #if !defined(COMPONENT_CAT1D)
_cyhal_clock_get_frequency_imo(const cyhal_clock_t * clock)1059 static uint32_t _cyhal_clock_get_frequency_imo(const cyhal_clock_t *clock)
1060 {
1061     CY_UNUSED_PARAMETER(clock);
1062     return CY_SYSCLK_IMO_FREQ;
1063 }
1064 #endif
1065 
1066 
1067 // ECO
1068 #if SRSS_ECO_PRESENT
_cyhal_clock_is_enabled_eco(const cyhal_clock_t * clock)1069 static bool _cyhal_clock_is_enabled_eco(const cyhal_clock_t *clock)
1070 {
1071     CY_UNUSED_PARAMETER(clock);
1072     return 0u != (SRSS_CLK_ECO_CONFIG & SRSS_CLK_ECO_CONFIG_ECO_EN_Msk);
1073 }
_cyhal_clock_set_enabled_eco(cyhal_clock_t * clock,bool enabled,bool wait_for_lock)1074 static cy_rslt_t _cyhal_clock_set_enabled_eco(cyhal_clock_t *clock, bool enabled, bool wait_for_lock)
1075 {
1076     CY_UNUSED_PARAMETER(clock);
1077 
1078     if (enabled)
1079     {
1080         if (0u != (SRSS_CLK_ECO_CONFIG & SRSS_CLK_ECO_CONFIG_ECO_EN_Msk))
1081         {
1082             // Already enabled
1083             if (wait_for_lock)
1084             {
1085                 for (int t = 0; t < 3 && Cy_SysClk_EcoGetStatus() != CY_SYSCLK_ECOSTAT_STABLE; ++t)
1086                 {
1087                     cyhal_system_delay_us(1000UL);
1088                 }
1089                 return Cy_SysClk_EcoGetStatus() == CY_SYSCLK_ECOSTAT_STABLE
1090                     ? CY_RSLT_SUCCESS
1091                     : CY_SYSCLK_TIMEOUT;
1092             }
1093             return CY_RSLT_SUCCESS;
1094         }
1095         else
1096         {
1097             return Cy_SysClk_EcoEnable(wait_for_lock ? 3000UL : 0UL);
1098         }
1099     }
1100     else
1101     {
1102         Cy_SysClk_EcoDisable();
1103         return CY_RSLT_SUCCESS;
1104     }
1105 }
_cyhal_clock_get_frequency_eco(const cyhal_clock_t * clock)1106 static uint32_t _cyhal_clock_get_frequency_eco(const cyhal_clock_t *clock)
1107 {
1108     CY_UNUSED_PARAMETER(clock);
1109     return Cy_SysClk_EcoGetFrequency();
1110 }
1111 #endif
1112 
1113 // EXT
_cyhal_clock_is_enabled_ext(const cyhal_clock_t * clock)1114 static bool _cyhal_clock_is_enabled_ext(const cyhal_clock_t *clock)
1115 {
1116     CY_UNUSED_PARAMETER(clock);
1117     return (Cy_SysClk_ExtClkGetFrequency() > 0);
1118 }
_cyhal_clock_get_frequency_ext(const cyhal_clock_t * clock)1119 static uint32_t _cyhal_clock_get_frequency_ext(const cyhal_clock_t *clock)
1120 {
1121     CY_UNUSED_PARAMETER(clock);
1122     return Cy_SysClk_ExtClkGetFrequency();
1123 }
_cyhal_clock_set_frequency_ext(cyhal_clock_t * clock,uint32_t hz,const cyhal_clock_tolerance_t * tolerance)1124 static cy_rslt_t _cyhal_clock_set_frequency_ext(cyhal_clock_t *clock, uint32_t hz, const cyhal_clock_tolerance_t *tolerance)
1125 {
1126     CY_UNUSED_PARAMETER(clock);
1127     CY_UNUSED_PARAMETER(tolerance);
1128 
1129     Cy_SysClk_ExtClkSetFrequency(hz);
1130     return CY_RSLT_SUCCESS;
1131 }
1132 
1133 // ALTHF
1134 #if SRSS_ALTHF_PRESENT
_cyhal_clock_is_enabled_althf(const cyhal_clock_t * clock)1135 static bool _cyhal_clock_is_enabled_althf(const cyhal_clock_t *clock)
1136 {
1137     CY_UNUSED_PARAMETER(clock);
1138     return (Cy_SysClk_AltHfGetFrequency() > 0);
1139 }
_cyhal_clock_get_frequency_althf(const cyhal_clock_t * clock)1140 static uint32_t _cyhal_clock_get_frequency_althf(const cyhal_clock_t *clock)
1141 {
1142     CY_UNUSED_PARAMETER(clock);
1143     return Cy_SysClk_AltHfGetFrequency();
1144 }
1145 #endif
1146 
1147 // ALTLF
1148 #if SRSS_ALTLF_PRESENT
_cyhal_clock_is_enabled_altlf(const cyhal_clock_t * clock)1149 static bool _cyhal_clock_is_enabled_altlf(const cyhal_clock_t *clock)
1150 {
1151     CY_UNUSED_PARAMETER(clock);
1152     return Cy_SysClk_AltLfIsEnabled();
1153 }
_cyhal_clock_get_frequency_altlf(const cyhal_clock_t * clock)1154 static uint32_t _cyhal_clock_get_frequency_altlf(const cyhal_clock_t *clock)
1155 {
1156     CY_UNUSED_PARAMETER(clock);
1157     return Cy_SysClk_AltLfGetFrequency();
1158 }
1159 #endif
1160 
1161 // IHO
1162 #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1D)
_cyhal_clock_is_enabled_iho(const cyhal_clock_t * clock)1163 static bool _cyhal_clock_is_enabled_iho(const cyhal_clock_t *clock)
1164 {
1165     CY_UNUSED_PARAMETER(clock);
1166     return Cy_SysClk_IhoIsEnabled();
1167 }
_cyhal_clock_set_enabled_iho(cyhal_clock_t * clock,bool enabled,bool wait_for_lock)1168 static cy_rslt_t _cyhal_clock_set_enabled_iho(cyhal_clock_t *clock, bool enabled, bool wait_for_lock)
1169 {
1170     CY_UNUSED_PARAMETER(clock);
1171     CY_UNUSED_PARAMETER(wait_for_lock);
1172 
1173     if (enabled)
1174         Cy_SysClk_IhoEnable();
1175     else
1176         Cy_SysClk_IhoDisable();
1177     return CY_RSLT_SUCCESS;
1178 }
_cyhal_clock_get_frequency_iho(const cyhal_clock_t * clock)1179 static uint32_t _cyhal_clock_get_frequency_iho(const cyhal_clock_t *clock)
1180 {
1181     CY_UNUSED_PARAMETER(clock);
1182     return CY_SYSCLK_IHO_FREQ;
1183 }
1184 #endif
1185 
1186 // ILO
1187 #if _CYHAL_SRSS_ILO_PRESENT
_cyhal_clock_is_enabled_ilo(const cyhal_clock_t * clock)1188 static bool _cyhal_clock_is_enabled_ilo(const cyhal_clock_t *clock)
1189 {
1190     CY_UNUSED_PARAMETER(clock);
1191     #if defined(COMPONENT_CAT1C) || (defined(COMPONENT_CAT1A) && defined(CY_SRSS_ILO_COUNT) && (CY_SRSS_ILO_COUNT > 1))
1192     return Cy_SysClk_IloSrcIsEnabled(clock->channel);
1193     #else
1194     return Cy_SysClk_IloIsEnabled();
1195     #endif
1196 }
_cyhal_clock_set_enabled_ilo(cyhal_clock_t * clock,bool enabled,bool wait_for_lock)1197 static cy_rslt_t _cyhal_clock_set_enabled_ilo(cyhal_clock_t *clock, bool enabled, bool wait_for_lock)
1198 {
1199     CY_UNUSED_PARAMETER(clock);
1200     CY_UNUSED_PARAMETER(wait_for_lock);
1201     #if (defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0))
1202     if (enabled)
1203     {
1204         Cy_SysPm_BgRefCtrl(true);
1205         Cy_WDT_Unlock();
1206         Cy_SysClk_IloSrcEnable(clock->channel);
1207         Cy_WDT_Lock();
1208     }
1209     else
1210     {
1211         Cy_SysPm_BgRefCtrl(false);
1212         Cy_WDT_Unlock();
1213         Cy_SysClk_IloSrcDisable(clock->channel);
1214         Cy_WDT_Lock();
1215     }
1216     #else
1217     if (enabled)
1218         Cy_SysClk_IloEnable();
1219     else
1220         Cy_SysClk_IloDisable();
1221     #endif
1222     return CY_RSLT_SUCCESS;
1223 }
_cyhal_clock_get_frequency_ilo(const cyhal_clock_t * clock)1224 static uint32_t _cyhal_clock_get_frequency_ilo(const cyhal_clock_t *clock)
1225 {
1226     CY_UNUSED_PARAMETER(clock);
1227     return CY_SYSCLK_ILO_FREQ;
1228 }
1229 #endif
1230 
1231 // PILO
1232 #if _CYHAL_SRSS_PILO_PRESENT
_cyhal_clock_is_enabled_pilo(const cyhal_clock_t * clock)1233 static bool _cyhal_clock_is_enabled_pilo(const cyhal_clock_t *clock)
1234 {
1235     CY_UNUSED_PARAMETER(clock);
1236     return Cy_SysClk_PiloIsEnabled();
1237 }
_cyhal_clock_set_enabled_pilo(cyhal_clock_t * clock,bool enabled,bool wait_for_lock)1238 static cy_rslt_t _cyhal_clock_set_enabled_pilo(cyhal_clock_t *clock, bool enabled, bool wait_for_lock)
1239 {
1240     CY_UNUSED_PARAMETER(clock);
1241     CY_UNUSED_PARAMETER(wait_for_lock);
1242 
1243     if (enabled)
1244         Cy_SysClk_PiloEnable();
1245     else
1246         Cy_SysClk_PiloDisable();
1247     return CY_RSLT_SUCCESS;
1248 }
_cyhal_clock_get_frequency_pilo(const cyhal_clock_t * clock)1249 static uint32_t _cyhal_clock_get_frequency_pilo(const cyhal_clock_t *clock)
1250 {
1251     CY_UNUSED_PARAMETER(clock);
1252     return CY_SYSCLK_PILO_FREQ;
1253 }
1254 #endif
1255 
1256 // WCO
1257 #if SRSS_BACKUP_PRESENT || SRSS_WCO_PRESENT
_cyhal_clock_is_enabled_wco(const cyhal_clock_t * clock)1258 static bool _cyhal_clock_is_enabled_wco(const cyhal_clock_t *clock)
1259 {
1260     CY_UNUSED_PARAMETER(clock);
1261 #if defined(CY_IP_MXS28SRSS)
1262     return 0u != (BACKUP_CTL & BACKUP_WCO_CTL_WCO_EN_Msk);
1263 #elif defined(CY_IP_MXS22SRSS)
1264     return 0u != (BACKUP_CTL & SRSS_CLK_WCO_CONFIG_WCO_EN_Msk);
1265 #else
1266     return 0u != (BACKUP_CTL & BACKUP_CTL_WCO_EN_Msk);
1267 #endif
1268 }
_cyhal_clock_set_enabled_wco(cyhal_clock_t * clock,bool enabled,bool wait_for_lock)1269 static cy_rslt_t _cyhal_clock_set_enabled_wco(cyhal_clock_t *clock, bool enabled, bool wait_for_lock)
1270 {
1271     CY_UNUSED_PARAMETER(clock);
1272 
1273     if (enabled)
1274     {
1275         cy_rslt_t rslt = Cy_SysClk_WcoEnable(wait_for_lock ? 1000000UL : 0UL);
1276         // Ignore CY_SYSCLK_TIMEOUT unless wait_for_lock is true
1277         return wait_for_lock ? rslt : CY_RSLT_SUCCESS;
1278     }
1279     else
1280     {
1281         Cy_SysClk_WcoDisable();
1282         return CY_RSLT_SUCCESS;
1283     }
1284 }
_cyhal_clock_get_frequency_wco(const cyhal_clock_t * clock)1285 static uint32_t _cyhal_clock_get_frequency_wco(const cyhal_clock_t *clock)
1286 {
1287     CY_UNUSED_PARAMETER(clock);
1288     return CY_SYSCLK_WCO_FREQ;
1289 }
1290 #endif
1291 
1292 // MFO
1293 #if defined(COMPONENT_CAT1B) || (SRSS_MFO_PRESENT)
_cyhal_clock_is_enabled_mfo(const cyhal_clock_t * clock)1294 static bool _cyhal_clock_is_enabled_mfo(const cyhal_clock_t *clock)
1295 {
1296     CY_UNUSED_PARAMETER(clock);
1297     return Cy_SysClk_MfoIsEnabled();
1298 }
_cyhal_clock_set_enabled_mfo(cyhal_clock_t * clock,bool enabled,bool wait_for_lock)1299 static cy_rslt_t _cyhal_clock_set_enabled_mfo(cyhal_clock_t *clock, bool enabled, bool wait_for_lock)
1300 {
1301     CY_UNUSED_PARAMETER(clock);
1302     CY_UNUSED_PARAMETER(wait_for_lock);
1303 
1304     if (enabled)
1305         // Enable the MFO but turn it off during deepsleep to reduce power consumption
1306         Cy_SysClk_MfoEnable(false);
1307     else
1308         Cy_SysClk_MfoDisable();
1309     return CY_RSLT_SUCCESS;
1310 }
_cyhal_clock_get_frequency_mfo(const cyhal_clock_t * clock)1311 static uint32_t _cyhal_clock_get_frequency_mfo(const cyhal_clock_t *clock)
1312 {
1313     CY_UNUSED_PARAMETER(clock);
1314     return CY_SYSCLK_MFO_FREQ;
1315 }
_cyhal_clock_get_sources_mfo(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)1316 static cy_rslt_t _cyhal_clock_get_sources_mfo(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
1317 {
1318     CY_UNUSED_PARAMETER(clock);
1319 
1320     static const cyhal_resource_inst_t *_CYHAL_CLOCK_SOURCE_MFO[] =
1321     {
1322         &CYHAL_CLOCK_RSC_IMO,
1323     };
1324 
1325     *sources = _CYHAL_CLOCK_SOURCE_MFO;
1326     *count = sizeof(_CYHAL_CLOCK_SOURCE_MFO) / sizeof(_CYHAL_CLOCK_SOURCE_MFO[0]);
1327     return CY_RSLT_SUCCESS;
1328 }
1329 #endif
1330 
1331 // PathMux
_cyhal_clock_get_frequency_pathmux(const cyhal_clock_t * clock)1332 static uint32_t _cyhal_clock_get_frequency_pathmux(const cyhal_clock_t *clock)
1333 {
1334     return Cy_SysClk_ClkPathMuxGetFrequency(clock->channel);
1335 }
_cyhal_clock_get_sources_pathmux(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)1336 static cy_rslt_t _cyhal_clock_get_sources_pathmux(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
1337 {
1338     CY_UNUSED_PARAMETER(clock);
1339 
1340     static const cyhal_resource_inst_t *_CYHAL_CLOCK_SOURCE_PATHMUX[] =
1341     {
1342     #if !defined(COMPONENT_CAT1D)
1343         &CYHAL_CLOCK_RSC_IMO,
1344     #endif
1345     #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1D)
1346         &CYHAL_CLOCK_RSC_IHO,
1347     #endif
1348     #if SRSS_ECO_PRESENT
1349         &CYHAL_CLOCK_RSC_ECO,
1350     #endif
1351         &CYHAL_CLOCK_RSC_EXT,
1352     #if SRSS_ALTHF_PRESENT
1353         &CYHAL_CLOCK_RSC_ALTHF,
1354     #endif
1355     #if (_CYHAL_SRSS_ILO_PRESENT)
1356     #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C)
1357         &CYHAL_CLOCK_RSC_ILO[0],
1358         #if (SRSS_HT_VARIANT > 0)
1359         &CYHAL_CLOCK_RSC_ILO[1],
1360         #endif
1361     #endif
1362     #endif
1363     #if _CYHAL_SRSS_PILO_PRESENT
1364         &CYHAL_CLOCK_RSC_PILO,
1365     #endif
1366     #if SRSS_BACKUP_PRESENT || SRSS_WCO_PRESENT
1367         &CYHAL_CLOCK_RSC_WCO,
1368     #endif
1369     #if SRSS_ALTLF_PRESENT
1370         &CYHAL_CLOCK_RSC_ALTLF,
1371     #endif
1372     };
1373 
1374     *sources = _CYHAL_CLOCK_SOURCE_PATHMUX;
1375     *count = sizeof(_CYHAL_CLOCK_SOURCE_PATHMUX) / sizeof(_CYHAL_CLOCK_SOURCE_PATHMUX[0]);
1376     return CY_RSLT_SUCCESS;
1377 }
1378 
_cyhal_clock_set_source_pathmux(cyhal_clock_t * clock,const cyhal_clock_t * source)1379 static cy_rslt_t _cyhal_clock_set_source_pathmux(cyhal_clock_t *clock, const cyhal_clock_t *source)
1380 {
1381     uint32_t new_freq;
1382     cy_en_clkpath_in_sources_t clkpath_src;
1383     switch (source->block)
1384     {
1385 #if !defined(COMPONENT_CAT1D)
1386         case CYHAL_CLOCK_BLOCK_IMO:
1387             clkpath_src = CY_SYSCLK_CLKPATH_IN_IMO;
1388             new_freq = CY_SYSCLK_IMO_FREQ;
1389             break;
1390 #endif
1391 #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1D)
1392         case CYHAL_CLOCK_BLOCK_IHO:
1393             clkpath_src = CY_SYSCLK_CLKPATH_IN_IHO;
1394             new_freq = CY_SYSCLK_IHO_FREQ;
1395             break;
1396 #endif
1397         case CYHAL_CLOCK_BLOCK_EXT:
1398             clkpath_src = CY_SYSCLK_CLKPATH_IN_EXT;
1399             new_freq = Cy_SysClk_ExtClkGetFrequency();
1400             break;
1401 #if SRSS_ECO_PRESENT
1402         case CYHAL_CLOCK_BLOCK_ECO:
1403             clkpath_src = CY_SYSCLK_CLKPATH_IN_ECO;
1404             new_freq = Cy_SysClk_EcoGetFrequency();
1405             break;
1406 #endif
1407 #if SRSS_ALTHF_PRESENT
1408         case CYHAL_CLOCK_BLOCK_ALTHF:
1409             clkpath_src = CY_SYSCLK_CLKPATH_IN_ALTHF;
1410             new_freq = Cy_SysClk_AltHfGetFrequency();
1411             break;
1412 #endif
1413 #if !defined(COMPONENT_CAT1D)
1414         case CYHAL_CLOCK_BLOCK_ILO:
1415         #if defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0)
1416             if (1 == source->channel)
1417             {
1418                 clkpath_src = CY_SYSCLK_CLKPATH_IN_ILO1;
1419                 new_freq = CY_SYSCLK_ILO_FREQ;
1420             }
1421             else
1422         #endif
1423             {
1424                 clkpath_src = CY_SYSCLK_CLKPATH_IN_ILO;
1425                 new_freq = CY_SYSCLK_ILO_FREQ;
1426             }
1427             break;
1428 #endif
1429 #if SRSS_BACKUP_PRESENT || SRSS_WCO_PRESENT
1430         case CYHAL_CLOCK_BLOCK_WCO:
1431             clkpath_src = CY_SYSCLK_CLKPATH_IN_WCO;
1432             new_freq = CY_SYSCLK_WCO_FREQ;
1433             break;
1434 #endif
1435 #if SRSS_ALTLF_PRESENT
1436         case CYHAL_CLOCK_BLOCK_ALTLF:
1437             clkpath_src = CY_SYSCLK_CLKPATH_IN_ALTLF;
1438             new_freq = Cy_SysClk_AltLfGetFrequency();
1439             break;
1440 #endif
1441 #if _CYHAL_SRSS_PILO_PRESENT
1442         case CYHAL_CLOCK_BLOCK_PILO:
1443             clkpath_src = CY_SYSCLK_CLKPATH_IN_PILO;
1444             new_freq = CY_SYSCLK_PILO_FREQ;
1445             break;
1446 #endif
1447         default:
1448             CY_ASSERT(false); //Unhandled clock
1449             return CYHAL_CLOCK_RSLT_ERR_SOURCE;
1450     }
1451 
1452     uint32_t old_hf_freq = Cy_SysClk_ClkHfGetFrequency(_CYHAL_CLOCK_CPU_HFCLK_IDX);
1453     uint32_t new_hf_freq = new_freq >> ((uint8_t)Cy_SysClk_ClkHfGetDivider(_CYHAL_CLOCK_CPU_HFCLK_IDX));
1454     bool is_sysclk_path = (clock->channel == (uint32_t)Cy_SysClk_ClkHfGetSource(_CYHAL_CLOCK_CPU_HFCLK_IDX));
1455 
1456     if (is_sysclk_path)
1457         _cyhal_clock_update_system_state(true, old_hf_freq, new_hf_freq);
1458 
1459     cy_rslt_t rslt = Cy_SysClk_ClkPathSetSource(clock->channel, clkpath_src);
1460 
1461     if (is_sysclk_path)
1462     {
1463         if (CY_RSLT_SUCCESS == rslt)
1464             _cyhal_clock_update_system_state(false, old_hf_freq, new_hf_freq);
1465         else // revert the change if there was one
1466             _cyhal_clock_update_system_state(false, new_hf_freq, old_hf_freq);
1467     }
1468 
1469     return rslt;
1470 }
1471 
1472 
1473 // FLL
1474 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C) || (SRSS_FLL_PRESENT)
_cyhal_clock_is_enabled_fll(const cyhal_clock_t * clock)1475 static bool _cyhal_clock_is_enabled_fll(const cyhal_clock_t *clock)
1476 {
1477     CY_UNUSED_PARAMETER(clock);
1478     return Cy_SysClk_FllIsEnabled();
1479 }
_cyhal_clock_set_enabled_fll(cyhal_clock_t * clock,bool enabled,bool wait_for_lock)1480 static cy_rslt_t _cyhal_clock_set_enabled_fll(cyhal_clock_t *clock, bool enabled, bool wait_for_lock)
1481 {
1482     CY_UNUSED_PARAMETER(clock);
1483     CY_UNUSED_PARAMETER(wait_for_lock);
1484 
1485     cy_stc_fll_manual_config_t cfg;
1486     Cy_SysClk_FllGetConfiguration(&cfg);
1487     uint32_t new_freq, old_freq;
1488     uint32_t div = (uint32_t)Cy_SysClk_ClkHfGetDivider(0);
1489     uint32_t src_freq = Cy_SysClk_ClkPathMuxGetFrequency(0);
1490     uint32_t fll_freq = CY_SYSLIB_DIV_ROUND((uint64_t)src_freq * (uint64_t)cfg.fllMult, (uint32_t)cfg.refDiv * ((cfg.enableOutputDiv) ? 2UL : 1UL));
1491     if (enabled)
1492     {
1493         new_freq = fll_freq >> div;
1494         old_freq = src_freq >> div;
1495     }
1496     else
1497     {
1498         new_freq = src_freq >> div;
1499         old_freq = fll_freq >> div;
1500     }
1501 
1502     bool fll_sources_cpu = (0 == (uint32_t)Cy_SysClk_ClkHfGetSource(_CYHAL_CLOCK_CPU_HFCLK_IDX));
1503     if (fll_sources_cpu)
1504         _cyhal_clock_update_system_state(true, old_freq, new_freq);
1505 
1506     cy_rslt_t rslt = (enabled)
1507         ? Cy_SysClk_FllEnable(wait_for_lock ? _CYHAL_CLOCK_FLL_LOCK_TIME : 0UL)
1508         : Cy_SysClk_FllDisable();
1509 
1510     if (fll_sources_cpu)
1511     {
1512         if (CY_RSLT_SUCCESS == rslt)
1513             _cyhal_clock_update_system_state(false, old_freq, new_freq);
1514         else // revert the change if there was one
1515             _cyhal_clock_update_system_state(false, new_freq, old_freq);
1516     }
1517 
1518     return rslt;
1519 }
_cyhal_clock_get_frequency_fll(const cyhal_clock_t * clock)1520 static uint32_t _cyhal_clock_get_frequency_fll(const cyhal_clock_t *clock)
1521 {
1522     CY_UNUSED_PARAMETER(clock);
1523     return Cy_SysClk_ClkPathGetFrequency(0);
1524 }
_cyhal_clock_set_frequency_fll(cyhal_clock_t * clock,uint32_t hz,const cyhal_clock_tolerance_t * tolerance)1525 static cy_rslt_t _cyhal_clock_set_frequency_fll(cyhal_clock_t *clock, uint32_t hz, const cyhal_clock_tolerance_t *tolerance)
1526 {
1527     CY_UNUSED_PARAMETER(clock);
1528     CY_UNUSED_PARAMETER(tolerance);
1529 
1530     cy_rslt_t rslt = CY_RSLT_SUCCESS;
1531     cy_stc_fll_manual_config_t cfg;
1532     Cy_SysClk_FllGetConfiguration(&cfg);
1533     uint32_t src_freq = Cy_SysClk_ClkPathMuxGetFrequency(0);
1534 
1535     if (0 == src_freq)
1536         rslt = CYHAL_CLOCK_RSLT_ERR_SOURCE;
1537     else
1538     {
1539         uint32_t old_freq = CY_SYSLIB_DIV_ROUND((uint64_t)src_freq * (uint64_t)cfg.fllMult, (uint32_t)cfg.refDiv * ((cfg.enableOutputDiv) ? 2UL : 1UL));
1540         uint32_t div = (uint32_t)Cy_SysClk_ClkHfGetDivider(0);
1541         uint32_t old_hf_freq = old_freq >> div;
1542         uint32_t new_hf_freq = hz /*new_freq*/ >> div;
1543 
1544         bool fll_sources_cpu = (0 == (uint32_t)Cy_SysClk_ClkHfGetSource(_CYHAL_CLOCK_CPU_HFCLK_IDX));
1545         if (fll_sources_cpu)
1546             _cyhal_clock_update_system_state(true, old_hf_freq, new_hf_freq);
1547 
1548         bool enabled = Cy_SysClk_FllIsEnabled();
1549         if (enabled)
1550             rslt = Cy_SysClk_FllDisable();
1551         if (CY_RSLT_SUCCESS == rslt)
1552         {
1553             rslt = Cy_SysClk_FllConfigure(src_freq, hz/*new_freq*/, CY_SYSCLK_FLLPLL_OUTPUT_AUTO);
1554 
1555             if (enabled)
1556             {
1557                 cy_rslt_t rslt2 = Cy_SysClk_FllEnable(_CYHAL_CLOCK_FLL_LOCK_TIME);
1558                 if (CY_RSLT_SUCCESS == rslt)
1559                     rslt = rslt2;
1560             }
1561         }
1562 
1563         if (fll_sources_cpu)
1564         {
1565             if (CY_RSLT_SUCCESS == rslt)
1566                 _cyhal_clock_update_system_state(false, old_hf_freq, new_hf_freq);
1567             else // revert the change if there was one
1568                 _cyhal_clock_update_system_state(false, new_hf_freq, old_hf_freq);
1569         }
1570     }
1571 
1572     return rslt;
1573 }
_cyhal_clock_get_sources_fll(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)1574 static cy_rslt_t _cyhal_clock_get_sources_fll(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
1575 {
1576     CY_UNUSED_PARAMETER(clock);
1577     *sources = &(_CYHAL_CLOCK_SOURCE_HF[1 + _CYHAL_SRSS_NUM_PLL]);
1578     *count = 1;
1579     return CY_RSLT_SUCCESS;
1580 }
1581 #endif
1582 
1583 // PLL
1584 #if (_CYHAL_SRSS_NUM_PLL > 0)
_cyhal_clock_is_enabled_pll(const cyhal_clock_t * clock)1585 static bool _cyhal_clock_is_enabled_pll(const cyhal_clock_t *clock)
1586 {
1587     #if defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0)
1588     if (clock->block == CYHAL_CLOCK_BLOCK_PLL200)
1589     {
1590         return Cy_SysClk_PllIsEnabled(clock->channel + 1 + SRSS_NUM_PLL400M);
1591     }
1592     #elif defined(COMPONENT_CAT1D)
1593     if (clock->block == CYHAL_CLOCK_BLOCK_DPLL500)
1594     {
1595         return Cy_SysClk_PllIsEnabled(clock->channel + 1 + SRSS_NUM_DPLL_LP);
1596     }
1597     #endif
1598     return Cy_SysClk_PllIsEnabled(clock->channel + 1);
1599 }
1600 
_cyhal_clock_extract_pll_params(cyhal_clock_t * clock,cy_stc_pll_manual_config_t * cfg,uint64_t * feedbackDiv,uint32_t * referenceDiv,uint32_t * outputDiv)1601 static void _cyhal_clock_extract_pll_params(cyhal_clock_t *clock, cy_stc_pll_manual_config_t *cfg, uint64_t *feedbackDiv,
1602         uint32_t *referenceDiv, uint32_t *outputDiv)
1603 {
1604     #if defined(CY_IP_MXS40SRSS)
1605     *feedbackDiv = cfg->feedbackDiv;
1606     *referenceDiv = cfg->referenceDiv;
1607     *outputDiv = cfg->outputDiv;
1608     CY_UNUSED_PARAMETER(clock);
1609     #elif defined(CY_IP_MXS22SRSS)
1610     if (clock->block == CYHAL_CLOCK_BLOCK_DPLL250)
1611     {
1612         *feedbackDiv = cfg->lpPllCfg->feedbackDiv;
1613         *referenceDiv = cfg->lpPllCfg->referenceDiv;
1614         *outputDiv = cfg->lpPllCfg->outputDiv;
1615     }
1616     else if (clock->block == CYHAL_CLOCK_BLOCK_DPLL500)
1617     {
1618         /* Per IP block documentation, each divider requires +1 for correct output clock calculation */
1619         *feedbackDiv = cfg->hpPllCfg->nDiv + 1;
1620         *referenceDiv = cfg->hpPllCfg->pDiv + 1;
1621         *outputDiv = cfg->hpPllCfg->kDiv + 1;
1622     }
1623     #else
1624         #error "Unhandled SRSS block type"
1625     #endif /* defined(CY_IP_MXS40SRSS) or defined(CY_IP_MXS22SRSS) or other (error) */
1626 }
1627 
_cyhal_clock_set_enabled_pll(cyhal_clock_t * clock,bool enabled,bool wait_for_lock)1628 static cy_rslt_t _cyhal_clock_set_enabled_pll(cyhal_clock_t *clock, bool enabled, bool wait_for_lock)
1629 {
1630     CY_UNUSED_PARAMETER(clock);
1631     CY_UNUSED_PARAMETER(wait_for_lock);
1632 
1633     //pll_idx is the path mux index (eg PLL number + 1) as used by PDL APIs
1634     uint32_t pll_idx = clock->channel + 1;
1635     #if defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0)
1636     if (clock->block == CYHAL_CLOCK_BLOCK_PLL200)
1637     {
1638         pll_idx = pll_idx + SRSS_NUM_PLL400M;
1639     }
1640     #elif defined(COMPONENT_CAT1D)
1641     if (clock->block == CYHAL_CLOCK_BLOCK_DPLL500)
1642     {
1643         pll_idx = pll_idx + SRSS_NUM_DPLL_LP;
1644     }
1645     #endif
1646     cy_stc_pll_manual_config_t cfg;
1647     cy_rslt_t rslt = Cy_SysClk_PllGetConfiguration(pll_idx, &cfg);
1648     if (CY_RSLT_SUCCESS == rslt)
1649     {
1650         uint32_t new_freq, old_freq;
1651         uint32_t div = (uint32_t)Cy_SysClk_ClkHfGetDivider(0);
1652         uint32_t src_freq = Cy_SysClk_ClkPathMuxGetFrequency(pll_idx);
1653 
1654         uint64_t feedbackDiv = 0;
1655         uint32_t referenceDiv = 0;
1656         uint32_t outputDiv = 0;
1657         _cyhal_clock_extract_pll_params(clock, &cfg, &feedbackDiv, &referenceDiv, &outputDiv);
1658 
1659         uint32_t pll_freq = CY_SYSLIB_DIV_ROUND((uint64_t)src_freq * feedbackDiv, referenceDiv * outputDiv);
1660 
1661         if (enabled)
1662         {
1663             new_freq = pll_freq >> div;
1664             old_freq = src_freq >> div;
1665         }
1666         else
1667         {
1668             new_freq = src_freq >> div;
1669             old_freq = pll_freq >> div;
1670         }
1671 
1672         bool pll_sources_cpu = (pll_idx == (uint32_t)Cy_SysClk_ClkHfGetSource(_CYHAL_CLOCK_CPU_HFCLK_IDX));
1673         if (pll_sources_cpu)
1674             _cyhal_clock_update_system_state(true, old_freq, new_freq);
1675 
1676         rslt = (enabled)
1677             ? Cy_SysClk_PllEnable(pll_idx, wait_for_lock ? _CYHAL_CLOCK_PLL_LOCK_TIME : 0UL)
1678             : Cy_SysClk_PllDisable(pll_idx);
1679 
1680         if (pll_sources_cpu)
1681         {
1682             if (CY_RSLT_SUCCESS == rslt)
1683                 _cyhal_clock_update_system_state(false, old_freq, new_freq);
1684             else // revert the change if there was one
1685                 _cyhal_clock_update_system_state(false, new_freq, old_freq);
1686         }
1687     }
1688 
1689     return rslt;
1690 }
_cyhal_clock_get_frequency_pll(const cyhal_clock_t * clock)1691 static uint32_t _cyhal_clock_get_frequency_pll(const cyhal_clock_t *clock)
1692 {
1693     #if defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0)
1694     if (clock->block == CYHAL_CLOCK_BLOCK_PLL200)
1695     {
1696         return Cy_SysClk_ClkPathGetFrequency(clock->channel + 1 + SRSS_NUM_PLL400M);
1697     }
1698     #elif defined(COMPONENT_CAT1D)
1699     if (clock->block == CYHAL_CLOCK_BLOCK_DPLL500)
1700     {
1701         return Cy_SysClk_ClkPathGetFrequency(clock->channel + 1 + SRSS_NUM_DPLL_LP);
1702     }
1703     #endif
1704     return Cy_SysClk_ClkPathGetFrequency(clock->channel + 1);
1705 }
_cyhal_clock_set_frequency_pll(cyhal_clock_t * clock,uint32_t hz,const cyhal_clock_tolerance_t * tolerance)1706 static cy_rslt_t _cyhal_clock_set_frequency_pll(cyhal_clock_t *clock, uint32_t hz, const cyhal_clock_tolerance_t *tolerance)
1707 {
1708     CY_UNUSED_PARAMETER(tolerance);
1709 
1710     cy_stc_pll_manual_config_t cfg;
1711     uint8_t pll_idx = clock->channel + 1;
1712     #if defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0)
1713     if (clock->block == CYHAL_CLOCK_BLOCK_PLL200)
1714     {
1715         pll_idx = pll_idx + SRSS_NUM_PLL400M;
1716     }
1717     #elif defined(COMPONENT_CAT1D)
1718     if (clock->block == CYHAL_CLOCK_BLOCK_DPLL500)
1719     {
1720         pll_idx = pll_idx + SRSS_NUM_DPLL_LP;
1721     }
1722     #endif
1723     cy_rslt_t rslt = Cy_SysClk_PllGetConfiguration(pll_idx, &cfg);
1724     if (CY_RSLT_SUCCESS == rslt)
1725     {
1726         bool enabled = Cy_SysClk_PllIsEnabled(pll_idx);
1727         if (enabled)
1728             rslt = Cy_SysClk_PllDisable(pll_idx);
1729         if (CY_RSLT_SUCCESS == rslt)
1730         {
1731             uint32_t src_freq = Cy_SysClk_ClkPathMuxGetFrequency(pll_idx);
1732 
1733             uint64_t feedbackDiv = 0;
1734             uint32_t referenceDiv = 0;
1735             uint32_t outputDiv = 0;
1736             _cyhal_clock_extract_pll_params(clock, &cfg, &feedbackDiv, &referenceDiv, &outputDiv);
1737 
1738             uint32_t old_freq = CY_SYSLIB_DIV_ROUND((uint64_t)src_freq * feedbackDiv, referenceDiv * outputDiv);
1739 
1740             uint32_t div = (uint32_t)Cy_SysClk_ClkHfGetDivider(0);
1741             uint32_t old_hf_freq = old_freq >> div;
1742             uint32_t new_hf_freq = hz/*new_freq*/ >> div;
1743 
1744             bool pll_sources_cpu = (pll_idx == (uint32_t)Cy_SysClk_ClkHfGetSource(_CYHAL_CLOCK_CPU_HFCLK_IDX));
1745             if (pll_sources_cpu)
1746                 _cyhal_clock_update_system_state(true, old_hf_freq, new_hf_freq);
1747 
1748             uint32_t input_hz = Cy_SysClk_ClkPathMuxGetFrequency(pll_idx);
1749             cy_stc_pll_config_t cfg2 =
1750             {
1751                 .inputFreq = input_hz,
1752                 .outputFreq = hz/*new_freq*/,
1753                 .lfMode = false,
1754                 .outputMode = CY_SYSCLK_FLLPLL_OUTPUT_AUTO,
1755             };
1756             rslt = Cy_SysClk_PllConfigure(pll_idx, &cfg2);
1757 
1758             if (enabled)
1759             {
1760                 cy_rslt_t rslt2 = Cy_SysClk_PllEnable(pll_idx, _CYHAL_CLOCK_PLL_LOCK_TIME);
1761                 if (CY_RSLT_SUCCESS == rslt)
1762                     rslt = rslt2;
1763             }
1764 
1765             if (pll_sources_cpu)
1766             {
1767                 if (CY_RSLT_SUCCESS == rslt)
1768                     _cyhal_clock_update_system_state(false, old_hf_freq, new_hf_freq);
1769                 else // revert the change if there was one
1770                     _cyhal_clock_update_system_state(false, new_hf_freq, old_hf_freq);
1771             }
1772         }
1773     }
1774 
1775     return rslt;
1776 }
_cyhal_clock_get_sources_pll(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)1777 static cy_rslt_t _cyhal_clock_get_sources_pll(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
1778 {
1779     // _CYHAL_CLOCK_SOURCE_HF has entries for FLL, PLL[n], PathMux[m]
1780 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C) || (SRSS_FLL_PRESENT)
1781     #if defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0)
1782     uint8_t channel = clock->channel;
1783     if (clock->block == CYHAL_CLOCK_BLOCK_PLL200)
1784     {
1785         channel = channel + SRSS_NUM_PLL400M;
1786     }
1787     *sources = &(_CYHAL_CLOCK_SOURCE_HF[2 + _CYHAL_SRSS_NUM_PLL + channel]);
1788     #else
1789     *sources = &(_CYHAL_CLOCK_SOURCE_HF[2 + _CYHAL_SRSS_NUM_PLL + clock->channel]); /* PATHMUX[n] entry is after the FLL (+1), PLLs (+num) and FLL path mux (+1) */
1790     #endif
1791 #elif defined(COMPONENT_CAT1D)
1792     uint8_t channel = clock->channel;
1793     if (clock->block == CYHAL_CLOCK_BLOCK_DPLL500)
1794     {
1795         channel = channel + SRSS_NUM_DPLL_LP;
1796     }
1797     *sources = &(_CYHAL_CLOCK_SOURCE_HF[_CYHAL_SRSS_NUM_PLL + channel]);
1798 #else
1799     *sources = &(_CYHAL_CLOCK_SOURCE_HF[_CYHAL_SRSS_NUM_PLL + clock->channel]); /* PATHMUX[n] entry is after the PLLs (+num) */
1800 #endif
1801     *count = 1;
1802     return CY_RSLT_SUCCESS;
1803 }
1804 #endif
1805 
1806 // MF
1807 #if defined(COMPONENT_CAT1B) || (SRSS_MFO_PRESENT) || defined(CY_IP_MXS22SRSS)
_cyhal_clock_is_enabled_mf(const cyhal_clock_t * clock)1808 static bool _cyhal_clock_is_enabled_mf(const cyhal_clock_t *clock)
1809 {
1810     CY_UNUSED_PARAMETER(clock);
1811     return Cy_SysClk_ClkMfIsEnabled();
1812 }
_cyhal_clock_set_enabled_mf(cyhal_clock_t * clock,bool enabled,bool wait_for_lock)1813 static cy_rslt_t _cyhal_clock_set_enabled_mf(cyhal_clock_t *clock, bool enabled, bool wait_for_lock)
1814 {
1815     CY_UNUSED_PARAMETER(clock);
1816     CY_UNUSED_PARAMETER(wait_for_lock);
1817 
1818     if (enabled)
1819         Cy_SysClk_ClkMfEnable();
1820     else
1821         Cy_SysClk_ClkMfDisable();
1822     return CY_RSLT_SUCCESS;
1823 }
_cyhal_clock_get_frequency_mf(const cyhal_clock_t * clock)1824 static uint32_t _cyhal_clock_get_frequency_mf(const cyhal_clock_t *clock)
1825 {
1826     CY_UNUSED_PARAMETER(clock);
1827     return Cy_SysClk_ClkMfGetFrequency();
1828 }
1829 #if defined(COMPONENT_CAT1D)
_cyhal_clock_get_source_frequency_mf()1830 static uint32_t _cyhal_clock_get_source_frequency_mf()
1831 {
1832     uint32_t output_freq = 0;
1833     cyhal_clock_t tmp_clk;
1834     cy_rslt_t result = ~CY_RSLT_SUCCESS;
1835     switch (Cy_SysClk_ClkMfGetSource())
1836     {
1837         case CY_SYSCLK_CLKMF_IN_IHO:
1838             result = cyhal_clock_get(&tmp_clk, &CYHAL_CLOCK_RSC_IHO);
1839             break;
1840         case CY_SYSCLK_CLKMF_IN_WCO:
1841             result = cyhal_clock_get(&tmp_clk, &CYHAL_CLOCK_RSC_WCO);
1842             break;
1843         default:
1844             /* Should never get here */
1845             CY_ASSERT(false);
1846     }
1847     if (CY_RSLT_SUCCESS == result)
1848     {
1849         output_freq = cyhal_clock_get_frequency(&tmp_clk);
1850     }
1851 
1852     return output_freq;
1853 }
1854 #endif
_cyhal_clock_set_frequency_mf(cyhal_clock_t * clock,uint32_t hz,const cyhal_clock_tolerance_t * tolerance)1855 static cy_rslt_t _cyhal_clock_set_frequency_mf(cyhal_clock_t *clock, uint32_t hz, const cyhal_clock_tolerance_t *tolerance)
1856 {
1857     CY_UNUSED_PARAMETER(clock);
1858 
1859     uint32_t div;
1860     #if defined(COMPONENT_CAT1D)
1861     cy_rslt_t rslt = _cyhal_clock_compute_div(_cyhal_clock_get_source_frequency_mf(), hz, 8, tolerance, &div);
1862     #else
1863     cy_rslt_t rslt = _cyhal_clock_compute_div(CY_SYSCLK_MFO_FREQ, hz, 8, tolerance, &div);
1864     #endif /* defined(COMPONENT_CAT1D) or other */
1865 
1866     if(false == CY_SYSCLK_IS_MF_DIVIDER_VALID(div))
1867         rslt = CYHAL_CLOCK_RSLT_ERR_FREQ;
1868 
1869     if (CY_RSLT_SUCCESS == rslt)
1870         Cy_SysClk_ClkMfSetDivider(div);
1871 
1872     return rslt;
1873 }
_cyhal_clock_set_divider_mf(cyhal_clock_t * clock,uint32_t divider)1874 static cy_rslt_t _cyhal_clock_set_divider_mf(cyhal_clock_t *clock, uint32_t divider)
1875 {
1876     CY_UNUSED_PARAMETER(clock);
1877 
1878     if (divider <= 256)
1879     {
1880         Cy_SysClk_ClkMfSetDivider(divider);
1881         return CY_RSLT_SUCCESS;
1882     }
1883     return CYHAL_CLOCK_RSLT_ERR_FREQ;
1884 }
_cyhal_clock_get_sources_mf(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)1885 static cy_rslt_t _cyhal_clock_get_sources_mf(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
1886 {
1887     CY_UNUSED_PARAMETER(clock);
1888 
1889     static const cyhal_resource_inst_t *_CYHAL_CLOCK_SOURCE_MF[] =
1890     {
1891         /* CAT1A only supports driving from the MFO */
1892     #if !defined(COMPONENT_CAT1D)
1893         &CYHAL_CLOCK_RSC_MFO,
1894     #endif
1895     #if _CYHAL_SRSS_ILO_PRESENT
1896         &CYHAL_CLOCK_RSC_ILO[0],
1897     #endif
1898     #if SRSS_BACKUP_PRESENT || SRSS_WCO_PRESENT
1899         &CYHAL_CLOCK_RSC_WCO,
1900     #endif
1901     #if _CYHAL_SRSS_PILO_PRESENT
1902         &CYHAL_CLOCK_RSC_PILO,
1903     #endif
1904     #if SRSS_ALTLF_PRESENT
1905         &CYHAL_CLOCK_RSC_ALTLF,
1906     #endif
1907     #if SRSS_ECO_PRESENT
1908         &CYHAL_CLOCK_RSC_ECO_PRESCALER,
1909     #endif
1910     #if SRSS_BACKUP_S40E_LPECO_PRESENT
1911         &CYHAL_CLOCK_RSC_LPECO_PRESCALER,
1912     #endif
1913     };
1914 
1915     *sources = _CYHAL_CLOCK_SOURCE_MF;
1916     *count = sizeof(_CYHAL_CLOCK_SOURCE_MF) / sizeof(_CYHAL_CLOCK_SOURCE_MF[0]);
1917     return CY_RSLT_SUCCESS;
1918 }
_cyhal_clock_set_source_mf(cyhal_clock_t * clock,const cyhal_clock_t * source)1919 static cy_rslt_t _cyhal_clock_set_source_mf(cyhal_clock_t *clock, const cyhal_clock_t *source)
1920 {
1921     CY_UNUSED_PARAMETER(clock);
1922 
1923     switch(source->block)
1924     {
1925 #if !defined(COMPONENT_CAT1D)
1926         case CYHAL_CLOCK_BLOCK_MFO:
1927             Cy_SysClk_ClkMfSetSource(CY_SYSCLK_CLKMF_IN_MFO);
1928             return CY_RSLT_SUCCESS;
1929 #else
1930         case CYHAL_CLOCK_BLOCK_IHO:
1931             Cy_SysClk_ClkMfSetSource(CY_SYSCLK_CLKMF_IN_IHO);
1932             return CY_RSLT_SUCCESS;
1933 #endif
1934 #if _CYHAL_SRSS_ILO_PRESENT
1935         case CYHAL_CLOCK_BLOCK_ILO:
1936             Cy_SysClk_ClkMfSetSource(CY_SYSCLK_CLKMF_IN_ILO);
1937             return CY_RSLT_SUCCESS;
1938 #endif
1939 #if SRSS_BACKUP_PRESENT || SRSS_WCO_PRESENT
1940         case CYHAL_CLOCK_BLOCK_WCO:
1941             Cy_SysClk_ClkMfSetSource(CY_SYSCLK_CLKMF_IN_WCO);
1942             return CY_RSLT_SUCCESS;
1943 #endif
1944 #if _CYHAL_SRSS_PILO_PRESENT
1945         case CYHAL_CLOCK_BLOCK_PILO:
1946             Cy_SysClk_ClkMfSetSource(CY_SYSCLK_CLKMF_IN_PILO);
1947             return CY_RSLT_SUCCESS;
1948 #endif
1949 #if SRSS_ALTLF_PRESENT
1950         case CYHAL_CLOCK_BLOCK_ALTLF:
1951             Cy_SysClk_ClkMfSetSource(CY_SYSCLK_CLKMF_IN_ALTLF);
1952             return CY_RSLT_SUCCESS;
1953 #endif
1954 #if SRSS_ECO_PRESENT
1955         case CYHAL_CLOCK_BLOCK_ECO_PRESCALER:
1956             Cy_SysClk_ClkMfSetSource(CY_SYSCLK_CLKMF_IN_ECO_PRESCALER);
1957             return CY_RSLT_SUCCESS;
1958 #endif
1959 #if SRSS_BACKUP_S40E_LPECO_PRESENT
1960         case CYHAL_CLOCK_BLOCK_LPECO_PRESCALER:
1961             Cy_SysClk_ClkMfSetSource(CY_SYSCLK_CLKMF_IN_LPECO);
1962             return CY_RSLT_SUCCESS;
1963 #endif
1964         default:
1965             CY_ASSERT(false); //Unhandled clock
1966             return CYHAL_CLOCK_RSLT_ERR_SOURCE;
1967     }
1968 }
1969 #endif
1970 
1971 // HF
_cyhal_clock_is_enabled_hf(const cyhal_clock_t * clock)1972 static bool _cyhal_clock_is_enabled_hf(const cyhal_clock_t *clock)
1973 {
1974     return Cy_SysClk_ClkHfIsEnabled(clock->channel);
1975 }
_cyhal_clock_set_enabled_hf(cyhal_clock_t * clock,bool enabled,bool wait_for_lock)1976 static cy_rslt_t _cyhal_clock_set_enabled_hf(cyhal_clock_t *clock, bool enabled, bool wait_for_lock)
1977 {
1978     CY_UNUSED_PARAMETER(wait_for_lock);
1979 
1980     return (enabled)
1981         ? Cy_SysClk_ClkHfEnable(clock->channel)
1982         : Cy_SysClk_ClkHfDisable(clock->channel);
1983 }
_cyhal_clock_get_frequency_hf(const cyhal_clock_t * clock)1984 static uint32_t _cyhal_clock_get_frequency_hf(const cyhal_clock_t *clock)
1985 {
1986     return Cy_SysClk_ClkHfGetFrequency(clock->channel);
1987 }
_cyhal_clock_set_divider_hf(cyhal_clock_t * clock,uint32_t divider)1988 static cy_rslt_t _cyhal_clock_set_divider_hf(cyhal_clock_t *clock, uint32_t divider)
1989 {
1990     cy_en_clkhf_dividers_t new_div;
1991     #if defined(CY_IP_MXS22SRSS)
1992     switch (divider)
1993     {
1994         case 1:
1995             new_div = CY_SYSCLK_CLKHF_NO_DIVIDE;
1996             break;
1997         case 2:
1998             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_2;
1999             break;
2000         case 3:
2001             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_3;
2002             break;
2003         case 4:
2004             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_4;
2005             break;
2006         case 5:
2007             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_5;
2008             break;
2009         case 6:
2010             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_6;
2011             break;
2012         case 7:
2013             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_7;
2014             break;
2015         case 8:
2016             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_8;
2017             break;
2018         case 9:
2019             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_9;
2020             break;
2021         case 10:
2022             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_10;
2023             break;
2024         case 11:
2025             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_11;
2026             break;
2027         case 12:
2028             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_12;
2029             break;
2030         case 13:
2031             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_13;
2032             break;
2033         case 14:
2034             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_14;
2035             break;
2036         case 15:
2037             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_15;
2038             break;
2039         case 16:
2040             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_16;
2041             break;
2042         default:
2043             return CYHAL_CLOCK_RSLT_ERR_FREQ;
2044     }
2045     #else
2046     switch (divider)
2047     {
2048         case 1:
2049             new_div = CY_SYSCLK_CLKHF_NO_DIVIDE;
2050             break;
2051         case 2:
2052             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_2;
2053             break;
2054         case 4:
2055             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_4;
2056             break;
2057         case 8:
2058             new_div = CY_SYSCLK_CLKHF_DIVIDE_BY_8;
2059             break;
2060         default:
2061             return CYHAL_CLOCK_RSLT_ERR_FREQ;
2062     }
2063     #endif
2064 
2065     /* Only used if updating HFClk 0 */
2066     uint32_t old_div = (uint32_t)Cy_SysClk_ClkHfGetDivider(0);
2067     uint32_t src = (uint32_t)Cy_SysClk_ClkHfGetSource(0);
2068     uint32_t path_freq = Cy_SysClk_ClkPathGetFrequency(src);
2069     uint32_t old_freq = path_freq >> old_div;
2070     uint32_t new_freq = path_freq >> ((uint32_t)new_div);
2071 
2072     if (0 == clock->channel)
2073         _cyhal_clock_update_system_state(true, old_freq, new_freq);
2074 
2075     cy_rslt_t rslt = (cy_rslt_t)Cy_SysClk_ClkHfSetDivider(clock->channel, new_div);
2076 
2077     if (0 == clock->channel)
2078     {
2079         if (CY_RSLT_SUCCESS == rslt)
2080             _cyhal_clock_update_system_state(false, old_freq, new_freq);
2081         else // revert the change if there was one
2082             _cyhal_clock_update_system_state(false, new_freq, old_freq);
2083     }
2084 
2085     return rslt;
2086 }
_cyhal_clock_get_sources_hf(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)2087 static cy_rslt_t _cyhal_clock_get_sources_hf(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
2088 {
2089     CY_UNUSED_PARAMETER(clock);
2090     *sources = _CYHAL_CLOCK_SOURCE_HF;
2091     *count = sizeof(_CYHAL_CLOCK_SOURCE_HF) / sizeof(_CYHAL_CLOCK_SOURCE_HF[0]);
2092     return CY_RSLT_SUCCESS;
2093 }
_cyhal_clock_set_source_hf(cyhal_clock_t * clock,const cyhal_clock_t * source)2094 static cy_rslt_t _cyhal_clock_set_source_hf(cyhal_clock_t *clock, const cyhal_clock_t *source)
2095 {
2096     uint32_t new_src;
2097     if (source->block == CYHAL_CLOCK_BLOCK_PATHMUX
2098 #if !defined(COMPONENT_CAT1D)
2099         || source->block == CYHAL_CLOCK_BLOCK_FLL
2100 #endif
2101     )
2102         new_src = source->channel;
2103 #if defined(COMPONENT_CAT1A) && !(defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0))
2104     else if (source->block == CYHAL_CLOCK_BLOCK_PLL)
2105 #elif defined(COMPONENT_CAT1B) || (defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0))
2106     else if ((source->block == CYHAL_CLOCK_BLOCK_PLL200) || (source->block == CYHAL_CLOCK_BLOCK_PLL400))
2107 #elif defined(COMPONENT_CAT1D)
2108     else if ((source->block == CYHAL_CLOCK_BLOCK_DPLL250) || (source->block == CYHAL_CLOCK_BLOCK_DPLL500))
2109 #endif
2110     {
2111         new_src = source->channel + 1;
2112 #if defined(SRSS_NUM_PLL400M) && (defined(COMPONENT_CAT1B) || (defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0)))
2113         if (source->block == CYHAL_CLOCK_BLOCK_PLL200)
2114         {
2115             /* As PLL200 and PLL400 has their own channels and PLL400 sits on lower PATH_MUX numbers
2116              * we need to increase calculated source num with respect to number of PLL400's */
2117             new_src += SRSS_NUM_PLL400M;
2118         }
2119 #endif /* defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C) */
2120     }
2121     else
2122         return CYHAL_CLOCK_RSLT_ERR_SOURCE;
2123 
2124     /* Only used if updating HFClk 0 */
2125     uint32_t div_cpu = (uint32_t)Cy_SysClk_ClkHfGetDivider(_CYHAL_CLOCK_CPU_HFCLK_IDX);
2126     uint32_t old_src_cpu = (uint32_t)Cy_SysClk_ClkHfGetSource(_CYHAL_CLOCK_CPU_HFCLK_IDX);
2127     uint32_t old_freq_cpu = Cy_SysClk_ClkPathGetFrequency(old_src_cpu) >> div_cpu;
2128     uint32_t new_freq_cpu = Cy_SysClk_ClkPathGetFrequency(new_src) >> div_cpu;
2129 
2130     if (_CYHAL_CLOCK_CPU_HFCLK_IDX == clock->channel)
2131         _cyhal_clock_update_system_state(true, old_freq_cpu, new_freq_cpu);
2132 
2133     cy_rslt_t rslt = Cy_SysClk_ClkHfSetSource(clock->channel, (cy_en_clkhf_in_sources_t)new_src);
2134 
2135     if (_CYHAL_CLOCK_CPU_HFCLK_IDX == clock->channel)
2136     {
2137         if (CY_RSLT_SUCCESS == rslt)
2138             _cyhal_clock_update_system_state(false, old_freq_cpu, new_freq_cpu);
2139         else // revert the change if there was one
2140             _cyhal_clock_update_system_state(false, new_freq_cpu, old_freq_cpu);
2141     }
2142 
2143     return rslt;
2144 }
2145 
2146 // LF
_cyhal_clock_get_frequency_lf(const cyhal_clock_t * clock)2147 static uint32_t _cyhal_clock_get_frequency_lf(const cyhal_clock_t *clock)
2148 {
2149     CY_UNUSED_PARAMETER(clock);
2150     return _cyhal_clock_get_lf_frequency();
2151 }
_cyhal_clock_get_sources_lf(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)2152 static cy_rslt_t _cyhal_clock_get_sources_lf(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
2153 {
2154     CY_UNUSED_PARAMETER(clock);
2155     static const cyhal_resource_inst_t *_CYHAL_CLOCK_SOURCE_LF[] =
2156     {
2157 #if _CYHAL_SRSS_ILO_PRESENT
2158     #if (defined(COMPONENT_CAT1C) || defined(COMPONENT_CAT1A))
2159         &CYHAL_CLOCK_RSC_ILO[0],
2160         #if (SRSS_HT_VARIANT > 0)
2161         &CYHAL_CLOCK_RSC_ILO[1],
2162         #endif
2163     #else
2164         &CYHAL_CLOCK_RSC_ILO[0],
2165     #endif
2166 #endif
2167     #if _CYHAL_SRSS_PILO_PRESENT
2168         &CYHAL_CLOCK_RSC_PILO,
2169     #endif
2170     #if SRSS_BACKUP_PRESENT || SRSS_WCO_PRESENT
2171         &CYHAL_CLOCK_RSC_WCO,
2172     #endif
2173     #if SRSS_ALTLF_PRESENT
2174         &CYHAL_CLOCK_RSC_ALTLF,
2175     #endif
2176 #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1D)
2177 #if SRSS_ECO_PRESENT
2178         &CYHAL_CLOCK_RSC_ECO_PRESCALER,
2179 #endif
2180 #if SRSS_BACKUP_S40E_LPECO_PRESENT
2181         &CYHAL_CLOCK_RSC_LPECO_PRESCALER,
2182 #endif
2183 #endif
2184     };
2185 
2186     *sources = _CYHAL_CLOCK_SOURCE_LF;
2187     *count = sizeof(_CYHAL_CLOCK_SOURCE_LF) / sizeof(_CYHAL_CLOCK_SOURCE_LF[0]);
2188     return CY_RSLT_SUCCESS;
2189 }
_cyhal_clock_set_source_lf(cyhal_clock_t * clock,const cyhal_clock_t * source)2190 static cy_rslt_t _cyhal_clock_set_source_lf(cyhal_clock_t *clock, const cyhal_clock_t *source)
2191 {
2192     CY_UNUSED_PARAMETER(clock);
2193     cy_rslt_t result = CY_RSLT_SUCCESS;
2194     #if defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0)
2195     Cy_WDT_Unlock();
2196     #endif
2197     switch (source->block)
2198     {
2199 #if _CYHAL_SRSS_ILO_PRESENT
2200         case CYHAL_CLOCK_BLOCK_ILO:
2201         #if defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0)
2202             if(1 == source->channel)
2203             {
2204                 Cy_SysClk_ClkLfSetSource(CY_SYSCLK_CLKLF_IN_ILO1);
2205             }
2206             else
2207         #endif
2208             {
2209                 Cy_SysClk_ClkLfSetSource(CY_SYSCLK_CLKLF_IN_ILO);
2210             }
2211             break;
2212 #endif
2213 #if SRSS_BACKUP_PRESENT || SRSS_WCO_PRESENT
2214         case CYHAL_CLOCK_BLOCK_WCO:
2215             Cy_SysClk_ClkLfSetSource(CY_SYSCLK_CLKLF_IN_WCO);
2216             break;
2217 #endif
2218 #if SRSS_ALTLF_PRESENT
2219         case CYHAL_CLOCK_BLOCK_ALTLF:
2220             Cy_SysClk_ClkLfSetSource(CY_SYSCLK_CLKLF_IN_ALTLF);
2221             break;
2222 #endif
2223 #if _CYHAL_SRSS_PILO_PRESENT
2224         case CYHAL_CLOCK_BLOCK_PILO:
2225             Cy_SysClk_ClkLfSetSource(CY_SYSCLK_CLKLF_IN_PILO);
2226             break;
2227 #endif
2228 #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1D)
2229 #if SRSS_ECO_PRESENT
2230         case CYHAL_CLOCK_BLOCK_ECO_PRESCALER:
2231             Cy_SysClk_ClkLfSetSource(CY_SYSCLK_CLKLF_IN_ECO_PRESCALER);
2232             break;
2233 #endif
2234 #if SRSS_BACKUP_S40E_LPECO_PRESENT
2235         case CYHAL_CLOCK_BLOCK_LPECO_PRESCALER:
2236             Cy_SysClk_ClkLfSetSource(CY_SYSCLK_CLKLF_IN_LPECO_PRESCALER);
2237             break;
2238 #endif
2239 #endif
2240         default:
2241             CY_ASSERT(false); //Unhandled clock
2242             result = CYHAL_CLOCK_RSLT_ERR_SOURCE;
2243     }
2244     #if defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0)
2245     Cy_WDT_Lock();
2246     #endif
2247     return result;
2248 }
2249 
2250 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C)
2251 // FAST
_cyhal_clock_get_frequency_fast(const cyhal_clock_t * clock)2252 static uint32_t _cyhal_clock_get_frequency_fast(const cyhal_clock_t *clock)
2253 {
2254     CY_UNUSED_PARAMETER(clock);
2255     #if defined(COMPONENT_CAT1A)
2256     return Cy_SysClk_ClkFastGetFrequency();
2257     #else
2258     return Cy_SysClk_ClkFastSrcGetFrequency(clock->channel);
2259     #endif
2260 }
_cyhal_clock_set_frequency_fast(cyhal_clock_t * clock,uint32_t hz,const cyhal_clock_tolerance_t * tolerance)2261 static cy_rslt_t _cyhal_clock_set_frequency_fast(cyhal_clock_t *clock, uint32_t hz, const cyhal_clock_tolerance_t *tolerance)
2262 {
2263     CY_UNUSED_PARAMETER(clock);
2264 
2265     uint32_t div;
2266     cy_rslt_t rslt;
2267     #if defined(COMPONENT_CAT1A)
2268     uint32_t input_hz = Cy_SysClk_ClkHfGetFrequency(0);
2269     rslt = _cyhal_clock_compute_div((uint64_t)input_hz, hz, 8, tolerance, &div);
2270     #else
2271     uint32_t input_hz = Cy_SysClk_ClkHfGetFrequency(1);
2272     rslt = _cyhal_clock_compute_div(((uint64_t)input_hz) << 5, hz, 13, tolerance, &div);
2273     #endif
2274 
2275     if (CY_RSLT_SUCCESS == rslt)
2276     {
2277         #if defined(COMPONENT_CAT1A)
2278         Cy_SysClk_ClkFastSetDivider((uint8_t)(div - 1));
2279         #else
2280         uint32_t div_int = (div >> 5) - 1;
2281         uint32_t div_frac = div & 0x1F;
2282         Cy_SysClk_ClkFastSrcSetDivider(clock->channel, (uint8_t)div_int, (uint8_t)div_frac);
2283         Cy_SysLib_SetWaitStates(false, 340);
2284         #endif
2285         SystemCoreClockUpdate();
2286     }
2287     return rslt;
2288 }
_cyhal_clock_set_divider_fast(cyhal_clock_t * clock,uint32_t divider)2289 static cy_rslt_t _cyhal_clock_set_divider_fast(cyhal_clock_t *clock, uint32_t divider)
2290 {
2291     CY_UNUSED_PARAMETER(clock);
2292 
2293     if (divider <= 256)
2294     {
2295         uint32_t divVal = divider - 1;
2296         #if defined(COMPONENT_CAT1A)
2297         Cy_SysClk_ClkFastSetDivider((uint8_t)divVal);
2298         #else
2299         Cy_SysClk_ClkFastSrcSetDivider(clock->channel, (uint8_t)divVal, 0);
2300         #endif
2301         SystemCoreClockUpdate();
2302         return CY_RSLT_SUCCESS;
2303     }
2304     return CYHAL_CLOCK_RSLT_ERR_FREQ;
2305 }
_cyhal_clock_get_sources_fast(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)2306 static cy_rslt_t _cyhal_clock_get_sources_fast(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
2307 {
2308     CY_UNUSED_PARAMETER(clock);
2309 
2310     static const cyhal_resource_inst_t *_CYHAL_CLOCK_SOURCE_FAST[] =
2311     {
2312         #if defined(COMPONENT_CAT1C)
2313         &CYHAL_CLOCK_RSC_HF[1],
2314         #else
2315         &CYHAL_CLOCK_RSC_HF[0],
2316         #endif
2317     };
2318 
2319     *sources = _CYHAL_CLOCK_SOURCE_FAST;
2320     *count = sizeof(_CYHAL_CLOCK_SOURCE_FAST) / sizeof(_CYHAL_CLOCK_SOURCE_FAST[0]);
2321     return CY_RSLT_SUCCESS;
2322 }
2323 
2324 // SLOW
_cyhal_clock_get_frequency_slow(const cyhal_clock_t * clock)2325 static uint32_t _cyhal_clock_get_frequency_slow(const cyhal_clock_t *clock)
2326 {
2327     CY_UNUSED_PARAMETER(clock);
2328     return Cy_SysClk_ClkSlowGetFrequency();
2329 }
_cyhal_clock_set_frequency_slow(cyhal_clock_t * clock,uint32_t hz,const cyhal_clock_tolerance_t * tolerance)2330 static cy_rslt_t _cyhal_clock_set_frequency_slow(cyhal_clock_t *clock, uint32_t hz, const cyhal_clock_tolerance_t *tolerance)
2331 {
2332     CY_UNUSED_PARAMETER(clock);
2333 
2334     uint32_t div;
2335 #if defined(CY_IP_M7CPUSS)
2336     uint32_t input_hz = Cy_SysClk_ClkMemGetFrequency();
2337 #else
2338     uint32_t input_hz = Cy_SysClk_ClkPeriGetFrequency();
2339 #endif
2340     cy_rslt_t rslt = _cyhal_clock_compute_div((uint64_t)input_hz, hz, 8, tolerance, &div);
2341 
2342     if (CY_RSLT_SUCCESS == rslt)
2343     {
2344         Cy_SysClk_ClkSlowSetDivider((uint8_t)(div - 1));
2345         SystemCoreClockUpdate();
2346     }
2347 
2348     return rslt;
2349 }
_cyhal_clock_set_divider_slow(cyhal_clock_t * clock,uint32_t divider)2350 static cy_rslt_t _cyhal_clock_set_divider_slow(cyhal_clock_t *clock, uint32_t divider)
2351 {
2352     CY_UNUSED_PARAMETER(clock);
2353 
2354     if (divider <= 256)
2355     {
2356         uint32_t divVal = divider - 1;
2357         Cy_SysClk_ClkSlowSetDivider((uint8_t)divVal);
2358         SystemCoreClockUpdate();
2359         return CY_RSLT_SUCCESS;
2360     }
2361     return CYHAL_CLOCK_RSLT_ERR_FREQ;
2362 }
_cyhal_clock_get_sources_slow(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)2363 static cy_rslt_t _cyhal_clock_get_sources_slow(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
2364 {
2365     CY_UNUSED_PARAMETER(clock);
2366     static const cyhal_resource_inst_t *_CYHAL_CLOCK_SOURCE_SLOW[] =
2367     {
2368         #if defined(COMPONENT_CAT1A)
2369         &CYHAL_CLOCK_RSC_PERI,
2370         #else
2371         &CYHAL_CLOCK_RSC_MEM,
2372         #endif
2373     };
2374 
2375     *sources = _CYHAL_CLOCK_SOURCE_SLOW;
2376     *count = sizeof(_CYHAL_CLOCK_SOURCE_SLOW) / sizeof(_CYHAL_CLOCK_SOURCE_SLOW[0]);
2377     return CY_RSLT_SUCCESS;
2378 }
2379 #endif
2380 #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1D)
2381 #if SRSS_ECO_PRESENT
2382 // ECO_PRESCALER - NOTE: This clock is not supported on any device yet
_cyhal_clock_get_frequency_eco_prescaler(const cyhal_clock_t * clock)2383 static uint32_t _cyhal_clock_get_frequency_eco_prescaler(const cyhal_clock_t *clock)
2384 {
2385     CY_UNUSED_PARAMETER(clock);
2386     //return Cy_SysClk_EcoPrescalerGetFrequency();
2387     return 0;
2388 }
_cyhal_clock_set_divider_eco_prescaler(cyhal_clock_t * clock,uint32_t divider)2389 static cy_rslt_t _cyhal_clock_set_divider_eco_prescaler(cyhal_clock_t *clock, uint32_t divider)
2390 {
2391     CY_UNUSED_PARAMETER(clock);
2392     CY_UNUSED_PARAMETER(divider);
2393 
2394     return CYHAL_CLOCK_RSLT_ERR_NOT_SUPPORTED;
2395 }
_cyhal_clock_get_sources_eco_prescaler(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)2396 static cy_rslt_t _cyhal_clock_get_sources_eco_prescaler(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
2397 {
2398     CY_UNUSED_PARAMETER(clock);
2399     CY_UNUSED_PARAMETER(sources);
2400     CY_UNUSED_PARAMETER(count);
2401 
2402     return CYHAL_CLOCK_RSLT_ERR_NOT_SUPPORTED;
2403 }
2404 #endif
2405 
2406 #if SRSS_BACKUP_S40E_LPECO_PRESENT
2407 // LPECO_PRESCALER - NOTE: This clock is not supported on any device yet
_cyhal_clock_get_frequency_lpeco_prescaler(const cyhal_clock_t * clock)2408 static uint32_t _cyhal_clock_get_frequency_lpeco_prescaler(const cyhal_clock_t *clock)
2409 {
2410     CY_UNUSED_PARAMETER(clock);
2411     return Cy_SysClk_LpEcoPrescalerGetFrequency();
2412 }
_cyhal_clock_set_divider_lpeco_prescaler(cyhal_clock_t * clock,uint32_t divider)2413 static cy_rslt_t _cyhal_clock_set_divider_lpeco_prescaler(cyhal_clock_t *clock, uint32_t divider)
2414 {
2415     CY_UNUSED_PARAMETER(clock);
2416     CY_UNUSED_PARAMETER(divider);
2417 
2418     return CYHAL_CLOCK_RSLT_ERR_NOT_SUPPORTED;
2419 }
_cyhal_clock_get_sources_lpeco_prescaler(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)2420 static cy_rslt_t _cyhal_clock_get_sources_lpeco_prescaler(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
2421 {
2422     CY_UNUSED_PARAMETER(clock);
2423     CY_UNUSED_PARAMETER(sources);
2424     CY_UNUSED_PARAMETER(count);
2425 
2426     return CYHAL_CLOCK_RSLT_ERR_NOT_SUPPORTED;
2427 }
2428 #endif
2429 #endif
2430 
2431 // MEM
2432 #if defined(CY_IP_M7CPUSS)
_cyhal_clock_set_divider_mem(cyhal_clock_t * clock,uint32_t divider)2433 static cy_rslt_t _cyhal_clock_set_divider_mem(cyhal_clock_t *clock, uint32_t divider)
2434 {
2435     CY_UNUSED_PARAMETER(clock);
2436     if (divider <= 256)
2437     {
2438         uint32_t divVal = divider - 1;
2439         Cy_SysClk_ClkMemSetDivider((uint8_t)divVal);
2440         SystemCoreClockUpdate();
2441         return CY_RSLT_SUCCESS;
2442     }
2443     return CYHAL_CLOCK_RSLT_ERR_FREQ;
2444 }
_cyhal_clock_get_frequency_mem(const cyhal_clock_t * clock)2445 static uint32_t _cyhal_clock_get_frequency_mem(const cyhal_clock_t *clock)
2446 {
2447     CY_UNUSED_PARAMETER(clock);
2448     return Cy_SysClk_ClkMemGetFrequency();
2449 }
_cyhal_clock_set_frequency_mem(cyhal_clock_t * clock,uint32_t hz,const cyhal_clock_tolerance_t * tolerance)2450 static cy_rslt_t _cyhal_clock_set_frequency_mem(cyhal_clock_t *clock, uint32_t hz, const cyhal_clock_tolerance_t *tolerance)
2451 {
2452     CY_UNUSED_PARAMETER(clock);
2453 
2454     uint32_t div;
2455     uint32_t input_hz = Cy_SysClk_ClkHfGetFrequency(0);
2456     cy_rslt_t rslt = _cyhal_clock_compute_div((uint64_t)input_hz, hz, 8, tolerance, &div);
2457     if (CY_RSLT_SUCCESS == rslt)
2458     {
2459         Cy_SysClk_ClkMemSetDivider((uint8_t)(div - 1));
2460         SystemCoreClockUpdate();
2461     }
2462     return rslt;
2463 }
_cyhal_clock_get_sources_mem(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)2464 static cy_rslt_t _cyhal_clock_get_sources_mem(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
2465 {
2466     CY_UNUSED_PARAMETER(clock);
2467 
2468     static const cyhal_resource_inst_t *_CYHAL_CLOCK_SOURCE_MEM[] =
2469     {
2470         &CYHAL_CLOCK_RSC_HF[0],
2471     };
2472     *sources = _CYHAL_CLOCK_SOURCE_MEM;
2473     *count = 1;
2474     return CY_RSLT_SUCCESS;
2475 }
2476 #endif
2477 
2478 // PERI
_cyhal_clock_get_frequency_peri(const cyhal_clock_t * clock)2479 static uint32_t _cyhal_clock_get_frequency_peri(const cyhal_clock_t *clock)
2480 {
2481     CY_UNUSED_PARAMETER(clock);
2482 #if defined(COMPONENT_CAT1C)
2483     if(clock->channel == 0)
2484 #endif
2485 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C)
2486     {
2487         return Cy_SysClk_ClkPeriGetFrequency();
2488     }
2489 #endif
2490 #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C) || defined(COMPONENT_CAT1D)
2491     #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C)
2492     uint8_t hfclk = _cyhal_utils_get_hfclk_for_peri_group(clock->channel);
2493     #elif defined(COMPONENT_CAT1D)
2494     uint8_t instance = _CYHAL_PERIPHERAL_CLOCK_GET_INSTANCE(clock->block);
2495     uint8_t group = _CYHAL_PERIPHERAL_CLOCK_GET_GROUP(clock->block);
2496     uint8_t hfclk = _cyhal_utils_get_hfclk_for_peri_group(_CYHAL_UTILS_PACK_INSTANCE_GROUP(instance, group));
2497     #endif /* defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C) or defined(COMPONENT_CAT1D) or other */
2498     return Cy_SysClk_ClkHfGetFrequency(hfclk) / (Cy_SysClk_PeriGroupGetDivider(clock->channel) + 1);
2499 #endif /* defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C) || defined(COMPONENT_CAT1D) */
2500 }
_cyhal_clock_set_frequency_peri(cyhal_clock_t * clock,uint32_t hz,const cyhal_clock_tolerance_t * tolerance)2501 static cy_rslt_t _cyhal_clock_set_frequency_peri(cyhal_clock_t *clock, uint32_t hz, const cyhal_clock_tolerance_t *tolerance)
2502 {
2503     CY_UNUSED_PARAMETER(clock);
2504 
2505     uint32_t div;
2506     cy_rslt_t result = CYHAL_CLOCK_RSLT_ERR_RESOURCE;
2507 #if defined(COMPONENT_CAT1C)
2508     if(clock->channel == 0)
2509 #endif
2510 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C)
2511     {
2512         uint32_t input_hz = Cy_SysClk_ClkHfGetFrequency(0);
2513         result = _cyhal_clock_compute_div((uint64_t)input_hz, hz, 8, tolerance, &div);
2514 
2515         if (CY_RSLT_SUCCESS == result)
2516         {
2517             Cy_SysClk_ClkPeriSetDivider((uint8_t)(div - 1));
2518             SystemCoreClockUpdate();
2519         }
2520     }
2521 #elif defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C) || defined(COMPONENT_CAT1D)
2522     #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C)
2523     uint32_t input_hz = Cy_SysClk_ClkHfGetFrequency(clock->channel == 1 ? 1 : 0);
2524     #elif defined(COMPONENT_CAT1D)
2525     uint8_t instance = _CYHAL_PERIPHERAL_CLOCK_GET_INSTANCE(clock->block);
2526     uint8_t group = _CYHAL_PERIPHERAL_CLOCK_GET_GROUP(clock->block);
2527     uint32_t input_hz = Cy_SysClk_ClkHfGetFrequency(_cyhal_utils_get_hfclk_for_peri_group(_CYHAL_UTILS_PACK_INSTANCE_GROUP(instance, group)));
2528     #endif /* defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C) or defined(COMPONENT_CAT1D) */
2529     result = _cyhal_clock_compute_div((uint64_t)input_hz, hz, 8, tolerance, &div);
2530 
2531 
2532     if (CY_RSLT_SUCCESS == result)
2533     {
2534         uint32_t group_num = clock->channel;
2535         #if defined(COMPONENT_CAT1D)
2536         /* I'm not completely confident in line below */
2537         group_num += _VAL2FLD(PERI_GR_INST_NUM, instance);
2538         #endif /* defined(COMPONENT_CAT1D) or other */
2539         Cy_SysClk_PeriGroupSetDivider(group_num, (uint8_t)(div - 1));
2540     }
2541 #endif /* defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C) || defined(COMPONENT_CAT1D) */
2542     return result;
2543 }
_cyhal_clock_set_divider_peri(cyhal_clock_t * clock,uint32_t divider)2544 static cy_rslt_t _cyhal_clock_set_divider_peri(cyhal_clock_t *clock, uint32_t divider)
2545 {
2546     CY_UNUSED_PARAMETER(clock);
2547     if (divider <= 256)
2548     {
2549         uint32_t divVal = divider - 1;
2550     #if defined(COMPONENT_CAT1C)
2551         if (clock->channel == 0)
2552     #endif
2553 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C)
2554         {
2555             Cy_SysClk_ClkPeriSetDivider((uint8_t)divVal);
2556             SystemCoreClockUpdate();
2557             return CY_RSLT_SUCCESS;
2558         }
2559 #endif
2560 #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C) || defined(COMPONENT_CAT1D)
2561         Cy_SysClk_PeriGroupSetDivider(clock->channel, (uint8_t)divVal);
2562         SystemCoreClockUpdate();
2563         return CY_RSLT_SUCCESS;
2564 #endif
2565     }
2566     return CYHAL_CLOCK_RSLT_ERR_FREQ;
2567 }
_cyhal_clock_get_sources_peri(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)2568 static cy_rslt_t _cyhal_clock_get_sources_peri(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
2569 {
2570     cy_rslt_t result = CYHAL_CLOCK_RSLT_ERR_RESOURCE;
2571 #if defined(COMPONENT_CAT1A)
2572     CY_UNUSED_PARAMETER(clock);
2573 #endif
2574 #if defined(COMPONENT_CAT1C)
2575     if (clock->channel == 0)
2576 #endif
2577 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C)
2578     {
2579         static const cyhal_resource_inst_t *_CYHAL_CLOCK_SOURCE_PERI[] =
2580         {
2581             &CYHAL_CLOCK_RSC_HF[0],
2582         };
2583 
2584         *sources = _CYHAL_CLOCK_SOURCE_PERI;
2585         *count = 1;
2586         result = CY_RSLT_SUCCESS;
2587     }
2588 #endif
2589 
2590 #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C) || defined(COMPONENT_CAT1D)
2591     #if defined(COMPONENT_CAT1C)
2592     else
2593     #endif
2594     {
2595     #if !defined(COMPONENT_CAT1D)
2596         uint8_t hfclk = _cyhal_utils_get_hfclk_for_peri_group(clock->channel);
2597     #else /* defined(COMPONENT_CAT1D) */
2598         uint8_t instance = _CYHAL_PERIPHERAL_CLOCK_GET_INSTANCE(clock->block);
2599         uint8_t group = _CYHAL_PERIPHERAL_CLOCK_GET_GROUP(clock->block);
2600         uint8_t hfclk = _cyhal_utils_get_hfclk_for_peri_group(_CYHAL_UTILS_PACK_INSTANCE_GROUP(instance, group));
2601     #endif /* !defined(COMPONENT_CAT1D) or other */
2602         result = _cyhal_clock_get_sources_peri_peripheral(hfclk, sources, count);
2603     }
2604 #endif
2605 
2606     return result;
2607 }
2608 
2609 /* PUMP clock is only available on CAT1A (SRSS V1) and CAT1B devices */
2610 #if PUMP_PRESENT
_cyhal_clock_is_enabled_pump(const cyhal_clock_t * clock)2611 static bool _cyhal_clock_is_enabled_pump(const cyhal_clock_t *clock)
2612 {
2613     CY_UNUSED_PARAMETER(clock);
2614     return Cy_SysClk_ClkPumpIsEnabled();
2615 }
_cyhal_clock_set_enabled_pump(cyhal_clock_t * clock,bool enabled,bool wait_for_lock)2616 static cy_rslt_t _cyhal_clock_set_enabled_pump(cyhal_clock_t *clock, bool enabled, bool wait_for_lock)
2617 {
2618     CY_UNUSED_PARAMETER(clock);
2619     CY_UNUSED_PARAMETER(wait_for_lock);
2620 
2621     if (enabled)
2622         Cy_SysClk_ClkPumpEnable();
2623     else
2624         Cy_SysClk_ClkPumpDisable();
2625     return CY_RSLT_SUCCESS;
2626 }
_cyhal_clock_get_frequency_pump(const cyhal_clock_t * clock)2627 static uint32_t _cyhal_clock_get_frequency_pump(const cyhal_clock_t *clock)
2628 {
2629     CY_UNUSED_PARAMETER(clock);
2630     return Cy_SysClk_ClkPumpGetFrequency();
2631 }
_cyhal_clock_set_divider_pump(cyhal_clock_t * clock,uint32_t divider)2632 static cy_rslt_t _cyhal_clock_set_divider_pump(cyhal_clock_t *clock, uint32_t divider)
2633 {
2634     CY_UNUSED_PARAMETER(clock);
2635 
2636     cy_en_clkpump_divide_t divVal;
2637     switch (divider)
2638     {
2639         case 1:
2640             divVal = CY_SYSCLK_PUMP_NO_DIV;
2641             break;
2642         case 2:
2643             divVal = CY_SYSCLK_PUMP_DIV_2;
2644             break;
2645         case 4:
2646             divVal = CY_SYSCLK_PUMP_DIV_4;
2647             break;
2648         case 8:
2649             divVal = CY_SYSCLK_PUMP_DIV_8;
2650             break;
2651         case 16:
2652             divVal = CY_SYSCLK_PUMP_DIV_16;
2653             break;
2654         default:
2655             return CYHAL_CLOCK_RSLT_ERR_FREQ;
2656     }
2657     Cy_SysClk_ClkPumpSetDivider(divVal);
2658     return CY_RSLT_SUCCESS;
2659 }
2660 #define _cyhal_clock_get_sources_pump	_cyhal_clock_get_sources_hf
_cyhal_clock_set_source_pump(cyhal_clock_t * clock,const cyhal_clock_t * source)2661 static cy_rslt_t _cyhal_clock_set_source_pump(cyhal_clock_t *clock, const cyhal_clock_t *source)
2662 {
2663     CY_UNUSED_PARAMETER(clock);
2664 
2665     if (source->block == CYHAL_CLOCK_BLOCK_PATHMUX || source->block == CYHAL_CLOCK_BLOCK_FLL)
2666     {
2667         Cy_SysClk_ClkPumpSetSource((cy_en_clkpump_in_sources_t)source->channel);
2668         return CY_RSLT_SUCCESS;
2669     }
2670 #if defined(COMPONENT_CAT1A)
2671     else if (source->block == CYHAL_CLOCK_BLOCK_PLL)
2672 #elif defined(COMPONENT_CAT1B)
2673     else if ((source->block == CYHAL_CLOCK_BLOCK_PLL200) || (source->block == CYHAL_CLOCK_BLOCK_PLL400))
2674 #endif
2675     {
2676         Cy_SysClk_ClkPumpSetSource((cy_en_clkpump_in_sources_t)(source->channel + 1));
2677         return CY_RSLT_SUCCESS;
2678     }
2679     else
2680         return CYHAL_CLOCK_RSLT_ERR_SOURCE;
2681 }
2682 #endif /* (defined(COMPONENT_CAT1A) && !(defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0))) || defined(COMPONENT_CAT1B) */
2683 
2684 // TIMER
2685 // TODO: Need to enable timer functionality for CAT1C once PDL team updates clk_timer API's
2686 #if defined(CY_IP_MXS40SRSS) && (CY_IP_MXS40SRSS_VERSION < 2)
_cyhal_clock_is_enabled_timer(const cyhal_clock_t * clock)2687 static bool _cyhal_clock_is_enabled_timer(const cyhal_clock_t *clock)
2688 {
2689     CY_UNUSED_PARAMETER(clock);
2690     return Cy_SysClk_ClkTimerIsEnabled();
2691 }
_cyhal_clock_set_enabled_timer(cyhal_clock_t * clock,bool enabled,bool wait_for_lock)2692 static cy_rslt_t _cyhal_clock_set_enabled_timer(cyhal_clock_t *clock, bool enabled, bool wait_for_lock)
2693 {
2694     CY_UNUSED_PARAMETER(clock);
2695     CY_UNUSED_PARAMETER(wait_for_lock);
2696 
2697     if (enabled)
2698         Cy_SysClk_ClkTimerEnable();
2699     else
2700         Cy_SysClk_ClkTimerDisable();
2701     return CY_RSLT_SUCCESS;
2702 }
_cyhal_clock_get_frequency_timer(const cyhal_clock_t * clock)2703 static uint32_t _cyhal_clock_get_frequency_timer(const cyhal_clock_t *clock)
2704 {
2705     CY_UNUSED_PARAMETER(clock);
2706     return Cy_SysClk_ClkTimerGetFrequency();
2707 }
_cyhal_clock_set_divider_timer(cyhal_clock_t * clock,uint32_t divider)2708 static cy_rslt_t _cyhal_clock_set_divider_timer(cyhal_clock_t *clock, uint32_t divider)
2709 {
2710     CY_UNUSED_PARAMETER(clock);
2711 
2712     if (divider <= 256)
2713     {
2714         uint32_t divVal = divider - 1;
2715         Cy_SysClk_ClkTimerSetDivider((uint8_t)divVal);
2716         return CY_RSLT_SUCCESS;
2717     }
2718     return CYHAL_CLOCK_RSLT_ERR_FREQ;
2719 }
_cyhal_clock_get_sources_timer(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)2720 static cy_rslt_t _cyhal_clock_get_sources_timer(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
2721 {
2722     CY_UNUSED_PARAMETER(clock);
2723     static const cyhal_resource_inst_t *_CYHAL_CLOCK_SOURCE_TIMER[] =
2724     {
2725         &CYHAL_CLOCK_RSC_IMO,
2726         &CYHAL_CLOCK_RSC_HF[0],
2727     };
2728 
2729     *sources = _CYHAL_CLOCK_SOURCE_TIMER;
2730     *count = sizeof(_CYHAL_CLOCK_SOURCE_TIMER) / sizeof(_CYHAL_CLOCK_SOURCE_TIMER[0]);
2731     return CY_RSLT_SUCCESS;
2732 }
_cyhal_clock_set_source_timer(cyhal_clock_t * clock,const cyhal_clock_t * source)2733 static cy_rslt_t _cyhal_clock_set_source_timer(cyhal_clock_t *clock, const cyhal_clock_t *source)
2734 {
2735     CY_UNUSED_PARAMETER(clock);
2736 
2737     if (source->block == CYHAL_CLOCK_BLOCK_IMO)
2738     {
2739         Cy_SysClk_ClkTimerSetSource(CY_SYSCLK_CLKTIMER_IN_IMO);
2740         return CY_RSLT_SUCCESS;
2741     }
2742     else if (source->block == CYHAL_CLOCK_BLOCK_HF && source->channel == 0)
2743     {
2744         Cy_SysClk_ClkTimerSetSource(CY_SYSCLK_CLKTIMER_IN_HF0_NODIV);
2745         return CY_RSLT_SUCCESS;
2746     }
2747     return CYHAL_CLOCK_RSLT_ERR_SOURCE;
2748 }
2749 #endif /* (CY_IP_MXS40SRSS) && (CY_IP_MXS40SRSS_VERSION < 2) */
2750 
2751 // BAK
_cyhal_clock_get_frequency_bak(const cyhal_clock_t * clock)2752 static uint32_t _cyhal_clock_get_frequency_bak(const cyhal_clock_t *clock)
2753 {
2754     CY_UNUSED_PARAMETER(clock);
2755     cy_en_clkbak_in_sources_t src = Cy_SysClk_ClkBakGetSource();
2756 #if SRSS_BACKUP_PRESENT
2757     if (src == CY_SYSCLK_BAK_IN_WCO)
2758         return CY_SYSCLK_WCO_FREQ;
2759 #else
2760     (void)src;
2761 #endif
2762     return _cyhal_clock_get_lf_frequency();
2763 }
_cyhal_clock_get_sources_bak(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)2764 static cy_rslt_t _cyhal_clock_get_sources_bak(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
2765 {
2766     CY_UNUSED_PARAMETER(clock);
2767     static const cyhal_resource_inst_t *_CYHAL_CLOCK_SOURCE_BAK[] =
2768     {
2769         &CYHAL_CLOCK_RSC_LF,
2770     #if SRSS_BACKUP_PRESENT || SRSS_WCO_PRESENT
2771         &CYHAL_CLOCK_RSC_WCO,
2772     #endif
2773     #if (_CYHAL_SRSS_ILO_PRESENT)
2774     #if defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0)
2775         &CYHAL_CLOCK_RSC_ILO[0],
2776     #elif defined(COMPONENT_CAT1B)
2777         &CYHAL_CLOCK_RSC_ILO[0],
2778     #endif
2779     #endif
2780     #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1D)
2781     #if _CYHAL_SRSS_PILO_PRESENT
2782         &CYHAL_CLOCK_RSC_PILO,
2783     #endif
2784     #endif
2785     #if defined(COMPONENT_CAT1B)
2786     #if SRSS_BACKUP_S40E_LPECO_PRESENT
2787         &CYHAL_CLOCK_RSC_LPECO_PRESCALER,
2788     #endif
2789     #endif
2790     };
2791 
2792     *sources = _CYHAL_CLOCK_SOURCE_BAK;
2793     *count = sizeof(_CYHAL_CLOCK_SOURCE_BAK) / sizeof(_CYHAL_CLOCK_SOURCE_BAK[0]);
2794     return CY_RSLT_SUCCESS;
2795 }
_cyhal_clock_set_source_bak(cyhal_clock_t * clock,const cyhal_clock_t * source)2796 static cy_rslt_t _cyhal_clock_set_source_bak(cyhal_clock_t *clock, const cyhal_clock_t *source)
2797 {
2798     CY_UNUSED_PARAMETER(clock);
2799 
2800     switch (source->block)
2801     {
2802         case CYHAL_CLOCK_BLOCK_WCO:
2803             Cy_SysClk_ClkBakSetSource(CY_SYSCLK_BAK_IN_WCO);
2804             return CY_RSLT_SUCCESS;
2805         case CYHAL_CLOCK_BLOCK_LF:
2806             Cy_SysClk_ClkBakSetSource(CY_SYSCLK_BAK_IN_CLKLF);
2807             return CY_RSLT_SUCCESS;
2808 #if defined(COMPONENT_CAT1B) || (defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0))
2809         case CYHAL_CLOCK_BLOCK_ILO:
2810             if(1 == source->channel)
2811             {
2812                 return CYHAL_CLOCK_RSLT_ERR_SOURCE;
2813             }
2814             Cy_SysClk_ClkBakSetSource(CY_SYSCLK_BAK_IN_ILO);
2815             return CY_RSLT_SUCCESS;
2816 #endif
2817 #if _CYHAL_SRSS_PILO_PRESENT && (defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C) || defined(COMPONENT_CAT1D))
2818         case CYHAL_CLOCK_BLOCK_PILO:
2819             Cy_SysClk_ClkBakSetSource(CY_SYSCLK_BAK_IN_PILO);
2820             return CY_RSLT_SUCCESS;
2821 #endif
2822 #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C)
2823 #if SRSS_BACKUP_S40E_LPECO_PRESENT
2824         case CYHAL_CLOCK_BLOCK_LPECO_PRESCALER:
2825             Cy_SysClk_ClkBakSetSource(CY_SYSCLK_BAK_IN_LPECO_PRESCALER);
2826             return CY_RSLT_SUCCESS;
2827 #endif
2828 #endif
2829         default:
2830             CY_ASSERT(false); //Unhandled clock
2831             return CYHAL_CLOCK_RSLT_ERR_SOURCE;
2832     }
2833 }
2834 
2835 #if !defined(COMPONENT_CAT1D)
2836 // ALT_SYS_TICK
_cyhal_clock_get_frequency_alt_sys_tick(const cyhal_clock_t * clock)2837 static uint32_t _cyhal_clock_get_frequency_alt_sys_tick(const cyhal_clock_t *clock)
2838 {
2839     CY_UNUSED_PARAMETER(clock);
2840     CY_ASSERT(false); // This is not supported at this time
2841     return 0;
2842 }
_cyhal_clock_get_sources_alt_sys_tick(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)2843 static cy_rslt_t _cyhal_clock_get_sources_alt_sys_tick(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
2844 {
2845     CY_UNUSED_PARAMETER(clock);
2846     static const cyhal_resource_inst_t *_CYHAL_CLOCK_SOURCE_ALT_SYS_TICK[] =
2847     {
2848     #if !defined(COMPONENT_CAT1D)
2849         &CYHAL_CLOCK_RSC_IMO,
2850     #endif
2851     #if SRSS_ECO_PRESENT
2852         &CYHAL_CLOCK_RSC_ECO,
2853     #endif
2854         &CYHAL_CLOCK_RSC_LF,
2855 #if (defined(CY_IP_MXS40SRSS) && (CY_IP_MXS40SRSS_VERSION < 2))
2856         &CYHAL_CLOCK_RSC_TIMER, /* Technically present on CAT1B and CAT1C, but deprecated */
2857 #endif
2858 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C)
2859 #if defined(COMPONENT_CAT1C)
2860         &CYHAL_CLOCK_RSC_FAST[0],
2861         &CYHAL_CLOCK_RSC_FAST[1],
2862 #else
2863         &CYHAL_CLOCK_RSC_FAST,
2864 #endif
2865         &CYHAL_CLOCK_RSC_SLOW,
2866 #elif defined(COMPONENT_CAT1B)
2867         &CYHAL_CLOCK_RSC_HF[0], /* CPU clock */
2868 #endif
2869     };
2870 
2871     *sources = _CYHAL_CLOCK_SOURCE_ALT_SYS_TICK;
2872     *count = sizeof(_CYHAL_CLOCK_SOURCE_ALT_SYS_TICK) / sizeof(_CYHAL_CLOCK_SOURCE_ALT_SYS_TICK[0]);
2873     return CY_RSLT_SUCCESS;
2874 }
_cyhal_clock_set_source_alt_sys_tick(cyhal_clock_t * clock,const cyhal_clock_t * source)2875 static cy_rslt_t _cyhal_clock_set_source_alt_sys_tick(cyhal_clock_t *clock, const cyhal_clock_t *source)
2876 {
2877     CY_UNUSED_PARAMETER(clock);
2878 
2879     switch (source->block)
2880     {
2881         case CYHAL_CLOCK_BLOCK_LF:
2882             Cy_SysTick_SetClockSource(CY_SYSTICK_CLOCK_SOURCE_CLK_LF);
2883             return CY_RSLT_SUCCESS;
2884 #if !defined(COMPONENT_CAT1D)
2885         case CYHAL_CLOCK_BLOCK_IMO:
2886             Cy_SysTick_SetClockSource(CY_SYSTICK_CLOCK_SOURCE_CLK_IMO);
2887             return CY_RSLT_SUCCESS;
2888 #endif
2889 #if SRSS_ECO_PRESENT
2890         case CYHAL_CLOCK_BLOCK_ECO:
2891             Cy_SysTick_SetClockSource(CY_SYSTICK_CLOCK_SOURCE_CLK_ECO);
2892             return CY_RSLT_SUCCESS;
2893 #endif
2894 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C)
2895 #if (defined(CY_IP_MXS40SRSS) && (CY_IP_MXS40SRSS_VERSION < 2))
2896         case CYHAL_CLOCK_BLOCK_TIMER:
2897             Cy_SysTick_SetClockSource(CY_SYSTICK_CLOCK_SOURCE_CLK_TIMER);
2898             return CY_RSLT_SUCCESS;
2899 #endif
2900         case CYHAL_CLOCK_BLOCK_FAST:
2901         case CYHAL_CLOCK_BLOCK_SLOW:
2902             Cy_SysTick_SetClockSource(CY_SYSTICK_CLOCK_SOURCE_CLK_CPU);
2903             return CY_RSLT_SUCCESS;
2904 #endif
2905         default:
2906             CY_ASSERT(false); //Unhandled clock
2907             return CYHAL_CLOCK_RSLT_ERR_SOURCE;
2908     }
2909 }
2910 #endif
2911 
2912 // Peripheral
2913 #if defined(COMPONENT_CAT1D)
_cyhal_clock_is_source_enabled_peripheral(const cyhal_clock_t * clock)2914 static bool _cyhal_clock_is_source_enabled_peripheral(const cyhal_clock_t *clock)
2915 {
2916     uint8_t instance = _CYHAL_PERIPHERAL_CLOCK_GET_INSTANCE(clock->block);
2917     uint8_t group = _CYHAL_PERIPHERAL_CLOCK_GET_GROUP(clock->block);
2918     uint8_t hfclk_idx = _cyhal_utils_get_hfclk_for_peri_group(_CYHAL_UTILS_PACK_INSTANCE_GROUP(instance, group));
2919     return Cy_SysClk_ClkHfIsEnabled(hfclk_idx);
2920 }
2921 #endif
2922 
_cyhal_clock_is_enabled_peripheral(const cyhal_clock_t * clock)2923 static bool _cyhal_clock_is_enabled_peripheral(const cyhal_clock_t *clock)
2924 {
2925     #if defined(COMPONENT_CAT1D)
2926     if (!_cyhal_clock_is_source_enabled_peripheral(clock))
2927     {
2928         /** Access to peri clock configuration registers will give no effect if
2929          * corresponding source HF clock is turned off. It needs to be turned on in order to proceed */
2930         CY_ASSERT(false);
2931         return false;
2932     }
2933     #endif
2934     return _cyhal_utils_peri_pclk_is_divider_enabled(_CYHAL_CLOCK_GET_PCLK_GR_NUM(clock->block), clock);
2935 }
_cyhal_clock_set_enabled_peripheral(cyhal_clock_t * clock,bool enabled,bool wait_for_lock)2936 static cy_rslt_t _cyhal_clock_set_enabled_peripheral(cyhal_clock_t *clock, bool enabled, bool wait_for_lock)
2937 {
2938     CY_UNUSED_PARAMETER(wait_for_lock);
2939 
2940     #if defined(COMPONENT_CAT1D)
2941     if (!_cyhal_clock_is_source_enabled_peripheral(clock))
2942     {
2943         /** Access to peri clock configuration registers will give no effect if
2944          * corresponding source HF clock is turned off. It needs to be turned on in order to proceed */
2945         return CYHAL_CLOCK_RSLT_ERR_SOURCE_DISABLED;
2946     }
2947     #endif
2948 
2949     return (enabled)
2950         ? _cyhal_utils_peri_pclk_enable_divider(_CYHAL_CLOCK_GET_PCLK_GR_NUM(clock->block), clock)
2951         : _cyhal_utils_peri_pclk_disable_divider(_CYHAL_CLOCK_GET_PCLK_GR_NUM(clock->block), clock);
2952 }
_cyhal_clock_get_frequency_peripheral(const cyhal_clock_t * clock)2953 static uint32_t _cyhal_clock_get_frequency_peripheral(const cyhal_clock_t *clock)
2954 {
2955     #if defined(COMPONENT_CAT1D)
2956     if (!_cyhal_clock_is_source_enabled_peripheral(clock))
2957     {
2958         /** Access to peri clock configuration registers will give no effect if
2959          * corresponding source HF clock is turned off. It needs to be turned on in order to proceed */
2960         CY_ASSERT(false);
2961         return 0;
2962     }
2963     #endif
2964     return _cyhal_utils_peri_pclk_get_frequency(_CYHAL_CLOCK_GET_PCLK_GR_NUM(clock->block), clock);
2965 }
_cyhal_clock_set_frequency_peripheral(cyhal_clock_t * clock,uint32_t hz,const cyhal_clock_tolerance_t * tolerance)2966 static cy_rslt_t _cyhal_clock_set_frequency_peripheral(cyhal_clock_t *clock, uint32_t hz, const cyhal_clock_tolerance_t *tolerance)
2967 {
2968     #if !defined(COMPONENT_CAT1D)
2969     CY_UNUSED_PARAMETER(clock);
2970     #endif
2971     CY_UNUSED_PARAMETER(tolerance);
2972 
2973     #if defined(COMPONENT_CAT1D)
2974     if (!_cyhal_clock_is_source_enabled_peripheral(clock))
2975     {
2976         /** Access to peri clock configuration registers will give no effect if
2977          * corresponding source HF clock is turned off. It needs to be turned on in order to proceed */
2978         return CYHAL_CLOCK_RSLT_ERR_SOURCE_DISABLED;
2979     }
2980     #endif
2981 
2982     // blocks 0b00 & 0b01 are integer, 0b10 & 0b11 are fractional
2983     uint32_t div;
2984 
2985 #if defined(CY_IP_MXPERI) && (CY_IP_MXPERI_VERSION <= 2) // CAT1A peri
2986     uint32_t input_hz = Cy_SysClk_ClkPeriGetFrequency();
2987 #elif defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C) || defined(COMPONENT_CAT1D)
2988     #if defined(COMPONENT_CAT1D)
2989     uint8_t instance = _CYHAL_PERIPHERAL_CLOCK_GET_INSTANCE(clock->block);
2990     uint8_t group = _CYHAL_PERIPHERAL_CLOCK_GET_GROUP(clock->block);
2991     uint8_t hfclk = _cyhal_utils_get_hfclk_for_peri_group(_CYHAL_UTILS_PACK_INSTANCE_GROUP(instance, group));
2992     #else /* !defined(COMPONENT_CAT1D) */
2993     uint8_t group = _CYHAL_PERIPHERAL_GROUP_GET_GROUP(clock->block);
2994     uint8_t hfclk = _cyhal_utils_get_hfclk_for_peri_group(group);
2995     #endif /* defined(COMPONENT_CAT1D) or other */
2996     #if defined(COMPONENT_CAT1C)
2997     /* Peri group 0 has clk_hf0 -> clk_peri, while group 1 just has clk_hf2 */
2998     uint32_t input_hz;
2999     if (group == 0)
3000     {
3001         input_hz = Cy_SysClk_ClkHfGetFrequency(hfclk) / (1 + (uint32_t)Cy_SysClk_ClkPeriGetDivider());
3002     }
3003     else
3004     {
3005         input_hz = Cy_SysClk_ClkHfGetFrequency(hfclk);
3006     }
3007     #else /* !defined(COMPONENT_CAT1C) */
3008     uint32_t input_hz = Cy_SysClk_ClkHfGetFrequency(hfclk);
3009     #endif /* defined(COMPONENT_CAT1C) */
3010 #endif
3011 
3012     if ((clock->block & 0x02) == 0) // Integer (8 or 16)
3013     {
3014         uint32_t bits = (clock->block & 0x01) ? 16 : 8;
3015         cy_rslt_t rslt = _cyhal_clock_compute_div((uint64_t)input_hz, hz, bits, tolerance, &div);
3016         return (CY_RSLT_SUCCESS == rslt)
3017             ? _cyhal_utils_peri_pclk_set_divider(_CYHAL_CLOCK_GET_PCLK_GR_NUM(clock->block), clock, (div - 1))
3018             : rslt;
3019     }
3020     else //Fractional (16.5 or 24.5)
3021     {
3022         // Multiply input by 32 so we can treat the 5 fractional bits as though they are extentions of the integer divider
3023         // Leave the the desired frequency alone, so we can just strip out the integer & fractional bits at the end.
3024         uint32_t bits = (clock->block & 0x01) ? 29 : 21; // Integer bits + 5
3025         cy_rslt_t rslt = _cyhal_clock_compute_div(((uint64_t)input_hz) << 5, hz, bits, tolerance, &div);
3026         if (CY_RSLT_SUCCESS == rslt)
3027         {
3028             uint32_t div_int = (div >> 5) - 1;
3029             uint32_t div_frac = div & 0x1F;
3030             return _cyhal_utils_peri_pclk_set_frac_divider(_CYHAL_CLOCK_GET_PCLK_GR_NUM(clock->block), clock, div_int, div_frac);
3031         }
3032         else
3033             return rslt;
3034     }
3035 }
_cyhal_clock_set_divider_peripheral(cyhal_clock_t * clock,uint32_t divider)3036 static cy_rslt_t _cyhal_clock_set_divider_peripheral(cyhal_clock_t *clock, uint32_t divider)
3037 {
3038     #if !defined(COMPONENT_CAT1D)
3039     CY_UNUSED_PARAMETER(clock);
3040     #else
3041     if (!_cyhal_clock_is_source_enabled_peripheral(clock))
3042     {
3043         /** Access to peri clock configuration registers will give no effect if
3044          * corresponding source HF clock is turned off. It needs to be turned on in order to proceed */
3045         return CYHAL_CLOCK_RSLT_ERR_SOURCE_DISABLED;
3046     }
3047     #endif
3048 
3049     // blocks 0b00 & 0b01 are integer, 0b10 & 0b11 are fractional
3050     return ((clock->block & 0x02) == 0)
3051         ? _cyhal_utils_peri_pclk_set_divider(_CYHAL_CLOCK_GET_PCLK_GR_NUM(clock->block), clock, divider - 1)
3052         : _cyhal_utils_peri_pclk_set_frac_divider(_CYHAL_CLOCK_GET_PCLK_GR_NUM(clock->block), clock, divider - 1, 0);
3053 }
_cyhal_clock_get_sources_peripheral(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)3054 static cy_rslt_t _cyhal_clock_get_sources_peripheral(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
3055 {
3056     cy_rslt_t result = CYHAL_CLOCK_RSLT_ERR_RESOURCE;
3057 #if defined(CY_IP_MXPERI) && (CY_IP_MXPERI_VERSION <= 2) // CAT1A peri
3058     result = _cyhal_clock_get_sources_slow(clock, sources, count);
3059 #elif defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1C) || defined(COMPONENT_CAT1D)
3060     #if defined(COMPONENT_CAT1D)
3061     uint8_t instance = _CYHAL_PERIPHERAL_CLOCK_GET_INSTANCE(clock->block);
3062     uint8_t group = _CYHAL_PERIPHERAL_CLOCK_GET_GROUP(clock->block);
3063     uint8_t hfclk = _cyhal_utils_get_hfclk_for_peri_group(_CYHAL_UTILS_PACK_INSTANCE_GROUP(instance, group));
3064     #else /* !defined(COMPONENT_CAT1D) */
3065     uint8_t group = _CYHAL_PERIPHERAL_GROUP_GET_GROUP(clock->block);
3066     uint8_t hfclk = _cyhal_utils_get_hfclk_for_peri_group(group);
3067     #endif /* defined(COMPONENT_CAT1D) or other */
3068     result = _cyhal_clock_get_sources_peri_peripheral(hfclk, sources, count);
3069 #endif
3070     return result;
3071 }
3072 
3073 
3074 
3075 /******************************************************************************
3076  ******************************* Clock Structs ********************************
3077  *****************************************************************************/
3078 
3079 /* Use a structure with function pointers to allow the driver to optimize out entire clocks if they
3080  * are not used. We make two exceptions to this. HF and peripheral clocks are called directly by
3081  * the public functions. This allows those clocks to be optimized based on what the user actually
3082  * calls. This distinction is done based on what the user is most likely to do with the HAL driver.
3083  * HF & peripheral clocks are likely to be configured at runtime based on setting up different
3084  * peripherals. Other system clocks are likely to be be set once at startup and never modified.
3085  * Based on this, we design the code so the compiler can optimize out the unused items most
3086  * efficiently.
3087  */
3088 
3089 typedef struct
3090 {
3091     bool (*is_enabled)(const cyhal_clock_t *clock);
3092     cy_rslt_t (*set_enabled)(cyhal_clock_t *clock, bool enabled, bool wait_for_lock);
3093     uint32_t (*get_frequency)(const cyhal_clock_t *clock);
3094     cy_rslt_t (*set_frequency)(cyhal_clock_t *clock, uint32_t hz, const cyhal_clock_tolerance_t *tolerance);
3095     cy_rslt_t (*set_divider)(cyhal_clock_t *clock, uint32_t divider);
3096     cy_rslt_t (*get_sources)(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count);
3097     cy_rslt_t (*set_source)(cyhal_clock_t *clock, const cyhal_clock_t *source);
3098     cyhal_clock_feature_t features;
3099 } cyhal_clock_funcs_t;
3100 
3101 #if !defined(COMPONENT_CAT1D)
3102 static const cyhal_clock_funcs_t FUNCS_IMO =
3103 {
3104     .features = CYHAL_CLOCK_FEATURE_NONE,
3105     .is_enabled = _cyhal_clock_is_enabled_true,
3106     .set_enabled = _cyhal_clock_set_enabled_unsupported,
3107     .get_frequency = _cyhal_clock_get_frequency_imo,
3108     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3109     .set_divider = _cyhal_clock_set_divider_unsupported,
3110     .get_sources = _cyhal_clock_get_sources_none,
3111     .set_source = _cyhal_clock_set_source_unsupported,
3112 };
3113 #endif
3114 
3115 #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1D)
3116 static const cyhal_clock_funcs_t FUNCS_IHO =
3117 {
3118     .features = CYHAL_CLOCK_FEATURE_ENABLE,
3119     .is_enabled = _cyhal_clock_is_enabled_iho,
3120     .set_enabled = _cyhal_clock_set_enabled_iho,
3121     .get_frequency = _cyhal_clock_get_frequency_iho,
3122     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3123     .set_divider = _cyhal_clock_set_divider_unsupported,
3124     .get_sources = _cyhal_clock_get_sources_none,
3125     .set_source = _cyhal_clock_set_source_unsupported,
3126 };
3127 #endif
3128 
3129 #if defined(COMPONENT_CAT1C)
3130 static const cyhal_clock_funcs_t FUNCS_MEM =
3131 {
3132     .features = (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_DIVIDER | CYHAL_CLOCK_FEATURE_FREQUENCY),
3133     .is_enabled = _cyhal_clock_is_enabled_true,
3134     .set_enabled = _cyhal_clock_set_enabled_unsupported,
3135     .get_frequency = _cyhal_clock_get_frequency_mem,
3136     .set_frequency = _cyhal_clock_set_frequency_mem,
3137     .set_divider = _cyhal_clock_set_divider_mem,
3138     .get_sources = _cyhal_clock_get_sources_mem,
3139     .set_source = _cyhal_clock_set_source_unsupported,
3140 };
3141 #endif
3142 
3143 #if SRSS_ECO_PRESENT
3144 static const cyhal_clock_funcs_t FUNCS_ECO =
3145 {
3146     .features = CYHAL_CLOCK_FEATURE_ENABLE,
3147     .is_enabled = _cyhal_clock_is_enabled_eco,
3148     .set_enabled = _cyhal_clock_set_enabled_eco,
3149     .get_frequency = _cyhal_clock_get_frequency_eco,
3150     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3151     .set_divider = _cyhal_clock_set_divider_unsupported,
3152     .get_sources = _cyhal_clock_get_sources_none,
3153     .set_source = _cyhal_clock_set_source_unsupported,
3154 };
3155 #endif
3156 
3157 static const cyhal_clock_funcs_t FUNCS_EXT =
3158 {
3159     .features = CYHAL_CLOCK_FEATURE_FREQUENCY,
3160     .is_enabled = _cyhal_clock_is_enabled_ext,
3161     .set_enabled = _cyhal_clock_set_enabled_unsupported,
3162     .get_frequency = _cyhal_clock_get_frequency_ext,
3163     .set_frequency = _cyhal_clock_set_frequency_ext,
3164     .set_divider = _cyhal_clock_set_divider_unsupported,
3165     .get_sources = _cyhal_clock_get_sources_none,
3166     .set_source = _cyhal_clock_set_source_unsupported,
3167 };
3168 
3169 #if SRSS_ALTHF_PRESENT
3170 static const cyhal_clock_funcs_t FUNCS_ALTHF =
3171 {
3172     .features = CYHAL_CLOCK_FEATURE_NONE,
3173     .is_enabled = _cyhal_clock_is_enabled_althf,
3174     .set_enabled = _cyhal_clock_set_enabled_unsupported,
3175     .get_frequency = _cyhal_clock_get_frequency_althf,
3176     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3177     .set_divider = _cyhal_clock_set_divider_unsupported,
3178     .get_sources = _cyhal_clock_get_sources_none,
3179     .set_source = _cyhal_clock_set_source_unsupported,
3180 };
3181 #endif
3182 
3183 #if SRSS_ALTLF_PRESENT
3184 static const cyhal_clock_funcs_t FUNCS_ALTLF =
3185 {
3186     .features = CYHAL_CLOCK_FEATURE_NONE,
3187     .is_enabled = _cyhal_clock_is_enabled_altlf,
3188     .set_enabled = _cyhal_clock_set_enabled_unsupported,
3189     .get_frequency = _cyhal_clock_get_frequency_altlf,
3190     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3191     .set_divider = _cyhal_clock_set_divider_unsupported,
3192     .get_sources = _cyhal_clock_get_sources_none,
3193     .set_source = _cyhal_clock_set_source_unsupported,
3194 };
3195 #endif
3196 
3197 #if _CYHAL_SRSS_ILO_PRESENT
3198 static const cyhal_clock_funcs_t FUNCS_ILO =
3199 {
3200     .features = CYHAL_CLOCK_FEATURE_ENABLE,
3201     .is_enabled = _cyhal_clock_is_enabled_ilo,
3202     .set_enabled = _cyhal_clock_set_enabled_ilo,
3203     .get_frequency = _cyhal_clock_get_frequency_ilo,
3204     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3205     .set_divider = _cyhal_clock_set_divider_unsupported,
3206     .get_sources = _cyhal_clock_get_sources_none,
3207     .set_source = _cyhal_clock_set_source_unsupported,
3208 };
3209 #endif
3210 
3211 #if _CYHAL_SRSS_PILO_PRESENT
3212 static const cyhal_clock_funcs_t FUNCS_PILO =
3213 {
3214     .features = CYHAL_CLOCK_FEATURE_ENABLE,
3215     .is_enabled = _cyhal_clock_is_enabled_pilo,
3216     .set_enabled = _cyhal_clock_set_enabled_pilo,
3217     .get_frequency = _cyhal_clock_get_frequency_pilo,
3218     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3219     .set_divider = _cyhal_clock_set_divider_unsupported,
3220     .get_sources = _cyhal_clock_get_sources_none,
3221     .set_source = _cyhal_clock_set_source_unsupported,
3222 };
3223 #endif
3224 
3225 #if SRSS_BACKUP_PRESENT || SRSS_WCO_PRESENT
3226 static const cyhal_clock_funcs_t FUNCS_WCO =
3227 {
3228     .features = CYHAL_CLOCK_FEATURE_ENABLE,
3229     .is_enabled = _cyhal_clock_is_enabled_wco,
3230     .set_enabled = _cyhal_clock_set_enabled_wco,
3231     .get_frequency = _cyhal_clock_get_frequency_wco,
3232     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3233     .set_divider = _cyhal_clock_set_divider_unsupported,
3234     .get_sources = _cyhal_clock_get_sources_none,
3235     .set_source = _cyhal_clock_set_source_unsupported,
3236 };
3237 #endif
3238 
3239 #if defined(COMPONENT_CAT1B) || (SRSS_MFO_PRESENT)
3240 static const cyhal_clock_funcs_t FUNCS_MFO =
3241 {
3242     .features = CYHAL_CLOCK_FEATURE_ENABLE,
3243     .is_enabled = _cyhal_clock_is_enabled_mfo,
3244     .set_enabled = _cyhal_clock_set_enabled_mfo,
3245     .get_frequency = _cyhal_clock_get_frequency_mfo,
3246     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3247     .set_divider = _cyhal_clock_set_divider_unsupported,
3248     .get_sources = _cyhal_clock_get_sources_mfo,
3249     .set_source = _cyhal_clock_set_source_unsupported,
3250 };
3251 #endif
3252 
3253 static const cyhal_clock_funcs_t FUNCS_PATHMUX =
3254 {
3255     .features = CYHAL_CLOCK_FEATURE_SOURCE,
3256     .is_enabled = _cyhal_clock_is_enabled_true,
3257     .set_enabled = _cyhal_clock_set_enabled_unsupported,
3258     .get_frequency = _cyhal_clock_get_frequency_pathmux,
3259     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3260     .set_divider = _cyhal_clock_set_divider_unsupported,
3261     .get_sources = _cyhal_clock_get_sources_pathmux,
3262     .set_source = _cyhal_clock_set_source_pathmux,
3263 };
3264 
3265 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C) || (SRSS_FLL_PRESENT)
3266 static const cyhal_clock_funcs_t FUNCS_FLL =
3267 {
3268     .features = (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_ENABLE | CYHAL_CLOCK_FEATURE_FREQUENCY),
3269     .is_enabled = _cyhal_clock_is_enabled_fll,
3270     .set_enabled = _cyhal_clock_set_enabled_fll,
3271     .get_frequency = _cyhal_clock_get_frequency_fll,
3272     .set_frequency = _cyhal_clock_set_frequency_fll,
3273     .set_divider = _cyhal_clock_set_divider_unsupported,
3274     .get_sources = _cyhal_clock_get_sources_fll,
3275     .set_source = _cyhal_clock_set_source_unsupported,
3276 };
3277 #endif
3278 
3279 #if (_CYHAL_SRSS_NUM_PLL > 0)
3280 static const cyhal_clock_funcs_t FUNCS_PLL =
3281 {
3282     .features = (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_ENABLE | CYHAL_CLOCK_FEATURE_FREQUENCY),
3283     .is_enabled = _cyhal_clock_is_enabled_pll,
3284     .set_enabled = _cyhal_clock_set_enabled_pll,
3285     .get_frequency = _cyhal_clock_get_frequency_pll,
3286     .set_frequency = _cyhal_clock_set_frequency_pll,
3287     .set_divider = _cyhal_clock_set_divider_unsupported,
3288     .get_sources = _cyhal_clock_get_sources_pll,
3289     .set_source = _cyhal_clock_set_source_unsupported,
3290 };
3291 #endif
3292 
3293 #if defined(COMPONENT_CAT1B) || (defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0))
3294 #if (SRSS_NUM_PLL > 0)
3295 #define FUNCS_PLL200 FUNCS_PLL
3296 #endif
3297 #if (SRSS_NUM_PLL400M > 0)
3298 #define FUNCS_PLL400 FUNCS_PLL
3299 #endif
3300 #endif /* defined(COMPONENT_CAT1C) */
3301 
3302 #if defined(COMPONENT_CAT1D)
3303 #if (SRSS_NUM_DPLL250M > 0)
3304 #define FUNCS_DPLL250 FUNCS_PLL
3305 #endif
3306 #if (SRSS_NUM_DPLL500M > 0)
3307 #define FUNCS_DPLL500 FUNCS_PLL
3308 #endif
3309 #endif /* defined(COMPONENT_CAT1D) */
3310 
3311 static const cyhal_clock_funcs_t FUNCS_LF =
3312 {
3313     .features = CYHAL_CLOCK_FEATURE_SOURCE,
3314     .is_enabled = _cyhal_clock_is_enabled_true,
3315     .set_enabled = _cyhal_clock_set_enabled_unsupported,
3316     .get_frequency = _cyhal_clock_get_frequency_lf,
3317     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3318     .set_divider = _cyhal_clock_set_divider_unsupported,
3319     .get_sources = _cyhal_clock_get_sources_lf,
3320     .set_source = _cyhal_clock_set_source_lf,
3321 };
3322 
3323 #if defined(COMPONENT_CAT1B) || (SRSS_MFO_PRESENT) || defined(CY_IP_MXS22SRSS)
3324 static const cyhal_clock_funcs_t FUNCS_MF =
3325 {
3326 #if (defined(CY_IP_MXS40SRSS) && (CY_IP_MXS40SRSS_VERSION < 2)) /* CAT1A/SRSSv1 only supports driving clk_mf from the MFO */
3327     .features = (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_ENABLE | CYHAL_CLOCK_FEATURE_DIVIDER | CYHAL_CLOCK_FEATURE_FREQUENCY),
3328 #else
3329     .features = (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_ENABLE | CYHAL_CLOCK_FEATURE_DIVIDER | CYHAL_CLOCK_FEATURE_FREQUENCY | CYHAL_CLOCK_FEATURE_SOURCE),
3330 #endif
3331     .is_enabled = _cyhal_clock_is_enabled_mf,
3332     .set_enabled = _cyhal_clock_set_enabled_mf,
3333     .get_frequency = _cyhal_clock_get_frequency_mf,
3334     .set_frequency = _cyhal_clock_set_frequency_mf,
3335     .set_divider = _cyhal_clock_set_divider_mf,
3336     .get_sources = _cyhal_clock_get_sources_mf,
3337     .set_source = _cyhal_clock_set_source_mf,
3338 };
3339 #endif
3340 
3341 static const cyhal_clock_funcs_t FUNCS_HF =
3342 {
3343     // NOTE: HF0 cannot be disabled, it would stop the MCUs. Ideally HF0 would not support
3344     // CYHAL_CLOCK_FEATURE_ENABLE, but this struct is never actually used in practice so it doesn't
3345     // matter.
3346     .features = (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_ENABLE | CYHAL_CLOCK_FEATURE_SOURCE | CYHAL_CLOCK_FEATURE_DIVIDER),
3347     .is_enabled = _cyhal_clock_is_enabled_hf,
3348     .set_enabled = _cyhal_clock_set_enabled_hf,
3349     .get_frequency = _cyhal_clock_get_frequency_hf,
3350     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3351     .set_divider = _cyhal_clock_set_divider_hf,
3352     .get_sources = _cyhal_clock_get_sources_hf,
3353     .set_source = _cyhal_clock_set_source_hf,
3354 };
3355 
3356 // PUMP clock is only available on CAT1A and CAT1B devices
3357 #if (PUMP_PRESENT)
3358 static const cyhal_clock_funcs_t FUNCS_PUMP =
3359 {
3360     .features = (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_ENABLE | CYHAL_CLOCK_FEATURE_SOURCE | CYHAL_CLOCK_FEATURE_DIVIDER),
3361     .is_enabled = _cyhal_clock_is_enabled_pump,
3362     .set_enabled = _cyhal_clock_set_enabled_pump,
3363     .get_frequency = _cyhal_clock_get_frequency_pump,
3364     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3365     .set_divider = _cyhal_clock_set_divider_pump,
3366     .get_sources = _cyhal_clock_get_sources_pump,
3367     .set_source = _cyhal_clock_set_source_pump,
3368 };
3369 #endif /* (PUMP_PRESENT) */
3370 
3371 #if (defined(CY_IP_MXS40SRSS) && (CY_IP_MXS40SRSS_VERSION < 2))
3372 static const cyhal_clock_funcs_t FUNCS_TIMER =
3373 {
3374     .features = (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_ENABLE | CYHAL_CLOCK_FEATURE_SOURCE | CYHAL_CLOCK_FEATURE_DIVIDER),
3375     .is_enabled = _cyhal_clock_is_enabled_timer,
3376     .set_enabled = _cyhal_clock_set_enabled_timer,
3377     .get_frequency = _cyhal_clock_get_frequency_timer,
3378     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3379     .set_divider = _cyhal_clock_set_divider_timer,
3380     .get_sources = _cyhal_clock_get_sources_timer,
3381     .set_source = _cyhal_clock_set_source_timer,
3382 };
3383 #endif /* #if (defined(CY_IP_MXS40SRSS) && (CY_IP_MXS40SRSS_VERSION < 2)) */
3384 
3385 static const cyhal_clock_funcs_t FUNCS_BAK =
3386 {
3387     .features = CYHAL_CLOCK_FEATURE_SOURCE,
3388     .is_enabled = _cyhal_clock_is_enabled_true,
3389     .set_enabled = _cyhal_clock_set_enabled_unsupported,
3390     .get_frequency = _cyhal_clock_get_frequency_bak,
3391     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3392     .set_divider = _cyhal_clock_set_divider_unsupported,
3393     .get_sources = _cyhal_clock_get_sources_bak,
3394     .set_source = _cyhal_clock_set_source_bak,
3395 };
3396 
3397 #if !defined(COMPONENT_CAT1D)
3398 static const cyhal_clock_funcs_t FUNCS_ALT_SYS_TICK =
3399 {
3400     .features = CYHAL_CLOCK_FEATURE_SOURCE,
3401     .is_enabled = _cyhal_clock_is_enabled_true,
3402     .set_enabled = _cyhal_clock_set_enabled_unsupported,
3403     .get_frequency = _cyhal_clock_get_frequency_alt_sys_tick,
3404     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3405     .set_divider = _cyhal_clock_set_divider_unsupported,
3406     .get_sources = _cyhal_clock_get_sources_alt_sys_tick,
3407     .set_source = _cyhal_clock_set_source_alt_sys_tick,
3408 };
3409 #endif
3410 
3411 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C)
3412 static const cyhal_clock_funcs_t FUNCS_FAST =
3413 {
3414     .features = (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_DIVIDER | CYHAL_CLOCK_FEATURE_FREQUENCY),
3415     .is_enabled = _cyhal_clock_is_enabled_true,
3416     .set_enabled = _cyhal_clock_set_enabled_unsupported,
3417     .get_frequency = _cyhal_clock_get_frequency_fast,
3418     .set_frequency = _cyhal_clock_set_frequency_fast,
3419     .set_divider = _cyhal_clock_set_divider_fast,
3420     .get_sources = _cyhal_clock_get_sources_fast,
3421     .set_source = _cyhal_clock_set_source_unsupported,
3422 };
3423 
3424 static const cyhal_clock_funcs_t FUNCS_SLOW =
3425 {
3426     .features = (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_DIVIDER | CYHAL_CLOCK_FEATURE_FREQUENCY),
3427     .is_enabled = _cyhal_clock_is_enabled_true,
3428     .set_enabled = _cyhal_clock_set_enabled_unsupported,
3429     .get_frequency = _cyhal_clock_get_frequency_slow,
3430     .set_frequency = _cyhal_clock_set_frequency_slow,
3431     .set_divider = _cyhal_clock_set_divider_slow,
3432     .get_sources = _cyhal_clock_get_sources_slow,
3433     .set_source = _cyhal_clock_set_source_unsupported,
3434 };
3435 #endif
3436 #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1D)
3437 #if SRSS_ECO_PRESENT
3438 static const cyhal_clock_funcs_t FUNCS_ECO_PRESCALER =
3439 {
3440     .features = (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_DIVIDER),
3441     .is_enabled = _cyhal_clock_is_enabled_true,
3442     .set_enabled = _cyhal_clock_set_enabled_unsupported,
3443     .get_frequency = _cyhal_clock_get_frequency_eco_prescaler,
3444     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3445     .set_divider = _cyhal_clock_set_divider_eco_prescaler,
3446     .get_sources = _cyhal_clock_get_sources_eco_prescaler,
3447     .set_source = _cyhal_clock_set_source_unsupported,
3448 };
3449 #endif
3450 
3451 #if SRSS_BACKUP_S40E_LPECO_PRESENT
3452 static const cyhal_clock_funcs_t FUNCS_LPECO_PRESCALER =
3453 {
3454     .features = (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_DIVIDER),
3455     .is_enabled = _cyhal_clock_is_enabled_true,
3456     .set_enabled = _cyhal_clock_set_enabled_unsupported,
3457     .get_frequency = _cyhal_clock_get_frequency_lpeco_prescaler,
3458     .set_frequency = _cyhal_clock_set_frequency_unsupported,
3459     .set_divider = _cyhal_clock_set_divider_lpeco_prescaler,
3460     .get_sources = _cyhal_clock_get_sources_lpeco_prescaler,
3461     .set_source = _cyhal_clock_set_source_unsupported,
3462 };
3463 #endif
3464 #endif
3465 
3466 static const cyhal_clock_funcs_t FUNCS_PERI =
3467 {
3468     .features = (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_DIVIDER | CYHAL_CLOCK_FEATURE_FREQUENCY),
3469     .is_enabled = _cyhal_clock_is_enabled_true,
3470     .set_enabled = _cyhal_clock_set_enabled_unsupported,
3471     .get_frequency = _cyhal_clock_get_frequency_peri,
3472     .set_frequency = _cyhal_clock_set_frequency_peri,
3473     .set_divider = _cyhal_clock_set_divider_peri,
3474     .get_sources = _cyhal_clock_get_sources_peri,
3475     .set_source = _cyhal_clock_set_source_unsupported,
3476 };
3477 
3478 static const cyhal_clock_funcs_t FUNCS_PERIPHERAL =
3479 {
3480     .features = (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_ENABLE | CYHAL_CLOCK_FEATURE_DIVIDER | CYHAL_CLOCK_FEATURE_FREQUENCY),
3481     .is_enabled = _cyhal_clock_is_enabled_peripheral,
3482     .set_enabled = _cyhal_clock_set_enabled_peripheral,
3483     .get_frequency = _cyhal_clock_get_frequency_peripheral,
3484     .set_frequency = _cyhal_clock_set_frequency_peripheral,
3485     .set_divider = _cyhal_clock_set_divider_peripheral,
3486     .get_sources = _cyhal_clock_get_sources_peripheral,
3487     .set_source = _cyhal_clock_set_source_unsupported,
3488 };
3489 
3490 
3491 static const cyhal_clock_funcs_t FUNCS_EMPTY =
3492 {
3493     .features = CYHAL_CLOCK_FEATURE_NONE,
3494     .is_enabled = NULL,
3495     .set_enabled = NULL,
3496     .get_frequency = NULL,
3497     .set_frequency = NULL,
3498     .set_divider = NULL,
3499     .get_sources = NULL,
3500     .set_source = NULL,
3501 };
3502 
_cyhal_clock_get_funcs_pathmux(void)3503 const void* _cyhal_clock_get_funcs_pathmux(void) { return &FUNCS_PATHMUX; }
3504 #if (_CYHAL_SRSS_NUM_PLL > 0)
_cyhal_clock_get_funcs_pll(void)3505 const void* _cyhal_clock_get_funcs_pll(void) { return &FUNCS_PLL; }
3506 #endif
3507 // HF and peripheral functions are called directly from the public APIs and do not go through
3508 // the struct lookup. This allows them to get optimized out based on what the user calls. We
3509 // return FUNCS_EMPTY here so as to avoid unnecessarily pulling in all functions for those clocks.
_cyhal_clock_get_funcs_hf(void)3510 const void* _cyhal_clock_get_funcs_hf(void) { return &FUNCS_EMPTY/*FUNCS_HF*/; }
_cyhal_clock_get_funcs_peripheral(void)3511 const void* _cyhal_clock_get_funcs_peripheral(void) { return &FUNCS_EMPTY/*FUNCS_PERIPHERAL*/; }
3512 
_cyhal_clock_get_funcs_all(cyhal_clock_block_t block)3513 static const cyhal_clock_funcs_t* _cyhal_clock_get_funcs_all(cyhal_clock_block_t block)
3514 {
3515     switch (block)
3516     {
3517 #if !defined(COMPONENT_CAT1D)
3518         case CYHAL_CLOCK_BLOCK_IMO:
3519             return &FUNCS_IMO;
3520 #endif
3521 #if SRSS_ECO_PRESENT
3522         case CYHAL_CLOCK_BLOCK_ECO:
3523             return &FUNCS_ECO;
3524 #endif
3525         case CYHAL_CLOCK_BLOCK_EXT:
3526             return &FUNCS_EXT;
3527 #if SRSS_ALTHF_PRESENT
3528         case CYHAL_CLOCK_BLOCK_ALTHF:
3529             return &FUNCS_ALTHF;
3530 #endif
3531 #if SRSS_ALTLF_PRESENT
3532         case CYHAL_CLOCK_BLOCK_ALTLF:
3533             return &FUNCS_ALTLF;
3534 #endif
3535 #if _CYHAL_SRSS_ILO_PRESENT
3536         case CYHAL_CLOCK_BLOCK_ILO:
3537             return &FUNCS_ILO;
3538 #endif
3539 #if _CYHAL_SRSS_PILO_PRESENT
3540         case CYHAL_CLOCK_BLOCK_PILO:
3541             return &FUNCS_PILO;
3542 #endif
3543 #if SRSS_BACKUP_PRESENT || SRSS_WCO_PRESENT
3544         case CYHAL_CLOCK_BLOCK_WCO:
3545             return &FUNCS_WCO;
3546 #endif
3547 #if defined(COMPONENT_CAT1B) || (SRSS_MFO_PRESENT)
3548         case CYHAL_CLOCK_BLOCK_MFO:
3549             return &FUNCS_MFO;
3550 #endif
3551         case CYHAL_CLOCK_BLOCK_PATHMUX:
3552             return &FUNCS_PATHMUX;
3553 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C) || (SRSS_FLL_PRESENT)
3554         case CYHAL_CLOCK_BLOCK_FLL:
3555             return &FUNCS_FLL;
3556 #endif
3557         case CYHAL_CLOCK_BLOCK_LF:
3558             return &FUNCS_LF;
3559 #if defined(COMPONENT_CAT1B) || (SRSS_MFO_PRESENT) || defined(CY_IP_MXS22SRSS)
3560         case CYHAL_CLOCK_BLOCK_MF:
3561             return &FUNCS_MF;
3562 #endif
3563         case CYHAL_CLOCK_BLOCK_HF:
3564             return &FUNCS_HF;
3565 // PUMP clock is only available on CAT1A and CAT1B devices
3566 #if (PUMP_PRESENT)
3567         case CYHAL_CLOCK_BLOCK_PUMP:
3568             return &FUNCS_PUMP;
3569 #endif /* (PUMP_PRESENT) */
3570         case CYHAL_CLOCK_BLOCK_BAK:
3571             return &FUNCS_BAK;
3572 #if !defined(COMPONENT_CAT1D)
3573         case CYHAL_CLOCK_BLOCK_ALT_SYS_TICK:
3574             return &FUNCS_ALT_SYS_TICK;
3575 #endif
3576         case CYHAL_CLOCK_BLOCK_PERI:
3577             return &FUNCS_PERI;
3578 #if (defined(CY_IP_MXS40SRSS) && (CY_IP_MXS40SRSS_VERSION < 2)) // CAT1A
3579     #if (_CYHAL_SRSS_NUM_PLL > 0)
3580         case CYHAL_CLOCK_BLOCK_PLL:
3581             return &FUNCS_PLL;
3582     #endif
3583 #endif
3584 #if defined(COMPONENT_CAT1C)
3585         case CYHAL_CLOCK_BLOCK_MEM:
3586             return &FUNCS_MEM;
3587 #endif
3588 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C)
3589     #if (defined(CY_IP_MXS40SRSS) && (CY_IP_MXS40SRSS_VERSION < 2))
3590         case CYHAL_CLOCK_BLOCK_TIMER:
3591             return &FUNCS_TIMER;
3592     #endif /* defined(CY_IP_MXS40SRSS) && (CY_IP_MXS40SRSS_VERSION < 2) */
3593         case CYHAL_CLOCK_BLOCK_FAST:
3594             return &FUNCS_FAST;
3595         case CYHAL_CLOCK_BLOCK_SLOW:
3596             return &FUNCS_SLOW;
3597 #endif
3598 #if defined(COMPONENT_CAT1B) || (defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0))
3599     #if (SRSS_NUM_PLL > 0)
3600         case CYHAL_CLOCK_BLOCK_PLL200:
3601             return &FUNCS_PLL200;
3602     #endif
3603     #if (SRSS_NUM_PLL400M > 0)
3604         case CYHAL_CLOCK_BLOCK_PLL400:
3605             return &FUNCS_PLL400;
3606     #endif /* (_CYHAL_SRSS_NUM_PLL > 0) */
3607 #endif
3608 #if defined(COMPONENT_CAT1D)
3609     #if (_CYHAL_SRSS_NUM_PLL > 0)
3610         case CYHAL_CLOCK_BLOCK_DPLL250:
3611             return &FUNCS_DPLL250;
3612         case CYHAL_CLOCK_BLOCK_DPLL500:
3613             return &FUNCS_DPLL500;
3614     #endif
3615 #endif
3616 #if defined(COMPONENT_CAT1B) || defined(COMPONENT_CAT1D)
3617         case CYHAL_CLOCK_BLOCK_IHO:
3618             return &FUNCS_IHO;
3619 #if SRSS_ECO_PRESENT
3620         case CYHAL_CLOCK_BLOCK_ECO_PRESCALER:
3621             return &FUNCS_ECO_PRESCALER;
3622 #endif
3623 #if SRSS_BACKUP_S40E_LPECO_PRESENT
3624         case CY_SYSCLK_CLKLF_IN_LPECO_PRESCALER:
3625             return &FUNCS_LPECO_PRESCALER;
3626 #endif
3627 #endif
3628         default:
3629             return &FUNCS_PERIPHERAL;
3630     }
3631 }
3632 
3633 #define _CYHAL_CLOCK_CREATE(x,y)	{ .block = (CYHAL_CLOCK_BLOCK_##x), .channel = (y), .reserved = false, .funcs = &(FUNCS_##x) }
3634 
3635 #if !defined(COMPONENT_CAT1D)
3636 const cyhal_clock_t CYHAL_CLOCK_IMO = _CYHAL_CLOCK_CREATE(IMO, 0);
3637 #endif
3638 const cyhal_clock_t CYHAL_CLOCK_EXT = _CYHAL_CLOCK_CREATE(EXT, 0);
3639 #if _CYHAL_SRSS_ILO_PRESENT
3640 const cyhal_clock_t CYHAL_CLOCK_ILO[_CYHAL_SRSS_NUM_ILO] =
3641 {
3642     _CYHAL_CLOCK_CREATE(ILO, 0),
3643     #if (SRSS_HT_VARIANT > 0)
3644     _CYHAL_CLOCK_CREATE(ILO, 1),
3645     #endif
3646 };
3647 #endif
3648 const cyhal_clock_t CYHAL_CLOCK_LF = _CYHAL_CLOCK_CREATE(LF, 0);
3649 // PUMP clock is only available on CAT1A and CAT1B devices
3650 #if (PUMP_PRESENT)
3651 const cyhal_clock_t CYHAL_CLOCK_PUMP = _CYHAL_CLOCK_CREATE(PUMP, 0);
3652 #endif /* (PUMP_PRESENT) */
3653 const cyhal_clock_t CYHAL_CLOCK_BAK = _CYHAL_CLOCK_CREATE(BAK, 0);
3654 #if !defined(COMPONENT_CAT1D)
3655 const cyhal_clock_t CYHAL_CLOCK_ALT_SYS_TICK = _CYHAL_CLOCK_CREATE(ALT_SYS_TICK, 0);
3656 #endif
3657 
3658 const cyhal_clock_t CYHAL_CLOCK_PATHMUX[SRSS_NUM_CLKPATH] =
3659 {
3660     _CYHAL_CLOCK_CREATE(PATHMUX, 0),
3661 #if (SRSS_NUM_CLKPATH > 1)
3662     _CYHAL_CLOCK_CREATE(PATHMUX, 1),
3663 #endif
3664 #if (SRSS_NUM_CLKPATH > 2)
3665     _CYHAL_CLOCK_CREATE(PATHMUX, 2),
3666 #endif
3667 #if (SRSS_NUM_CLKPATH > 3)
3668     _CYHAL_CLOCK_CREATE(PATHMUX, 3),
3669 #endif
3670 #if (SRSS_NUM_CLKPATH > 4)
3671     _CYHAL_CLOCK_CREATE(PATHMUX, 4),
3672 #endif
3673 #if (SRSS_NUM_CLKPATH > 5)
3674     _CYHAL_CLOCK_CREATE(PATHMUX, 5),
3675 #endif
3676 #if (SRSS_NUM_CLKPATH > 6)
3677     _CYHAL_CLOCK_CREATE(PATHMUX, 6),
3678 #endif
3679 #if (SRSS_NUM_CLKPATH > 7)
3680     _CYHAL_CLOCK_CREATE(PATHMUX, 7),
3681 #endif
3682 #if (SRSS_NUM_CLKPATH > 8)
3683     _CYHAL_CLOCK_CREATE(PATHMUX, 8),
3684 #endif
3685 #if (SRSS_NUM_CLKPATH > 9)
3686     _CYHAL_CLOCK_CREATE(PATHMUX, 9),
3687 #endif
3688 #if (SRSS_NUM_CLKPATH > 10)
3689     _CYHAL_CLOCK_CREATE(PATHMUX, 10),
3690 #endif
3691 #if (SRSS_NUM_CLKPATH > 11)
3692     _CYHAL_CLOCK_CREATE(PATHMUX, 11),
3693 #endif
3694 #if (SRSS_NUM_CLKPATH > 12)
3695     _CYHAL_CLOCK_CREATE(PATHMUX, 12),
3696 #endif
3697 #if (SRSS_NUM_CLKPATH > 13)
3698     _CYHAL_CLOCK_CREATE(PATHMUX, 13),
3699 #endif
3700 #if (SRSS_NUM_CLKPATH > 14)
3701     _CYHAL_CLOCK_CREATE(PATHMUX, 14),
3702 #endif
3703 #if (SRSS_NUM_CLKPATH > 15)
3704     _CYHAL_CLOCK_CREATE(PATHMUX, 15),
3705 #endif
3706 };
3707 
3708 const cyhal_clock_t CYHAL_CLOCK_HF[SRSS_NUM_HFROOT] =
3709 {
3710     _CYHAL_CLOCK_CREATE(HF, 0),
3711 #if (SRSS_NUM_HFROOT > 1)
3712     _CYHAL_CLOCK_CREATE(HF, 1),
3713 #endif
3714 #if (SRSS_NUM_HFROOT > 2)
3715     _CYHAL_CLOCK_CREATE(HF, 2),
3716 #endif
3717 #if (SRSS_NUM_HFROOT > 3)
3718     _CYHAL_CLOCK_CREATE(HF, 3),
3719 #endif
3720 #if (SRSS_NUM_HFROOT > 4)
3721     _CYHAL_CLOCK_CREATE(HF, 4),
3722 #endif
3723 #if (SRSS_NUM_HFROOT > 5)
3724     _CYHAL_CLOCK_CREATE(HF, 5),
3725 #endif
3726 #if (SRSS_NUM_HFROOT > 6)
3727     _CYHAL_CLOCK_CREATE(HF, 6),
3728 #endif
3729 #if (SRSS_NUM_HFROOT > 7)
3730     _CYHAL_CLOCK_CREATE(HF, 7),
3731 #endif
3732 #if (SRSS_NUM_HFROOT > 8)
3733     _CYHAL_CLOCK_CREATE(HF, 8),
3734 #endif
3735 #if (SRSS_NUM_HFROOT > 9)
3736     _CYHAL_CLOCK_CREATE(HF, 9),
3737 #endif
3738 #if (SRSS_NUM_HFROOT > 10)
3739     _CYHAL_CLOCK_CREATE(HF, 10),
3740 #endif
3741 #if (SRSS_NUM_HFROOT > 11)
3742     _CYHAL_CLOCK_CREATE(HF, 11),
3743 #endif
3744 #if (SRSS_NUM_HFROOT > 12)
3745     _CYHAL_CLOCK_CREATE(HF, 12),
3746 #endif
3747 #if (SRSS_NUM_HFROOT > 13)
3748     _CYHAL_CLOCK_CREATE(HF, 13),
3749 #endif
3750 #if (SRSS_NUM_HFROOT > 14)
3751     _CYHAL_CLOCK_CREATE(HF, 14),
3752 #endif
3753 #if (SRSS_NUM_HFROOT > 15)
3754     _CYHAL_CLOCK_CREATE(HF, 15),
3755 #endif
3756 };
3757 
3758 #if SRSS_ECO_PRESENT
3759 const cyhal_clock_t CYHAL_CLOCK_ECO = _CYHAL_CLOCK_CREATE(ECO, 0);
3760 #endif
3761 #if SRSS_ALTHF_PRESENT
3762 const cyhal_clock_t CYHAL_CLOCK_ALTHF = _CYHAL_CLOCK_CREATE(ALTHF, 0);
3763 #endif
3764 #if SRSS_ALTLF_PRESENT
3765 const cyhal_clock_t CYHAL_CLOCK_ALTLF = _CYHAL_CLOCK_CREATE(ALTLF, 0);
3766 #endif
3767 #if _CYHAL_SRSS_PILO_PRESENT
3768 const cyhal_clock_t CYHAL_CLOCK_PILO = _CYHAL_CLOCK_CREATE(PILO, 0);
3769 #endif
3770 #if SRSS_BACKUP_PRESENT || SRSS_WCO_PRESENT
3771 const cyhal_clock_t CYHAL_CLOCK_WCO = _CYHAL_CLOCK_CREATE(WCO, 0);
3772 #endif
3773 #if defined(COMPONENT_CAT1B) || (SRSS_MFO_PRESENT)
3774 const cyhal_clock_t CYHAL_CLOCK_MFO = _CYHAL_CLOCK_CREATE(MFO, 0);
3775 const cyhal_clock_t CYHAL_CLOCK_MF = _CYHAL_CLOCK_CREATE(MF, 0);
3776 #endif
3777 #if defined(COMPONENT_CAT1C)
3778 const cyhal_clock_t CYHAL_CLOCK_MEM = _CYHAL_CLOCK_CREATE(MEM, 0);
3779 #endif
3780 
3781 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C) || (SRSS_FLL_PRESENT)
3782 const cyhal_clock_t CYHAL_CLOCK_FLL = _CYHAL_CLOCK_CREATE(FLL, 0);
3783 #endif
3784 
3785 #if defined(COMPONENT_CAT1A) || defined(COMPONENT_CAT1C)
3786 #if defined(COMPONENT_CAT1C)
3787 const cyhal_clock_t CYHAL_CLOCK_FAST[2] =
3788 {
3789     _CYHAL_CLOCK_CREATE(FAST, 0),
3790     _CYHAL_CLOCK_CREATE(FAST, 1),
3791 };
3792 #else
3793 const cyhal_clock_t CYHAL_CLOCK_FAST = _CYHAL_CLOCK_CREATE(FAST, 0);
3794 #endif
3795 const cyhal_clock_t CYHAL_CLOCK_SLOW = _CYHAL_CLOCK_CREATE(SLOW, 0);
3796 // Enable the peri clock for all CAT1A devices.
3797 #if defined(COMPONENT_CAT1A)
3798     const cyhal_clock_t CYHAL_CLOCK_PERI = _CYHAL_CLOCK_CREATE(PERI, 0);
3799     // Enable the timer clock for all CAT1A devices other than TVBIIE
3800     #if defined(CY_IP_MXS40SRSS) && (CY_IP_MXS40SRSS_VERSION < 2)
3801         const cyhal_clock_t CYHAL_CLOCK_TIMER = _CYHAL_CLOCK_CREATE(TIMER, 0);
3802     #endif /* defined(CY_IP_MXS40SRSS) && (CY_IP_MXS40SRSS_VERSION < 2) */
3803 #endif /*defined(COMPONENT_CAT1A) */
3804 
3805 #if (_CYHAL_SRSS_NUM_PLL > 0) && defined(COMPONENT_CAT1A) && !(defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0))
3806 const cyhal_clock_t CYHAL_CLOCK_PLL[_CYHAL_SRSS_NUM_PLL] =
3807 {
3808     _CYHAL_CLOCK_CREATE(PLL, 0),
3809 #if (_CYHAL_SRSS_NUM_PLL > 1)
3810     _CYHAL_CLOCK_CREATE(PLL, 1),
3811 #endif
3812 #if (_CYHAL_SRSS_NUM_PLL > 2)
3813     _CYHAL_CLOCK_CREATE(PLL, 2),
3814 #endif
3815 #if (_CYHAL_SRSS_NUM_PLL > 3)
3816     _CYHAL_CLOCK_CREATE(PLL, 3),
3817 #endif
3818 #if (_CYHAL_SRSS_NUM_PLL > 4)
3819     _CYHAL_CLOCK_CREATE(PLL, 4),
3820 #endif
3821 #if (_CYHAL_SRSS_NUM_PLL > 5)
3822     _CYHAL_CLOCK_CREATE(PLL, 5),
3823 #endif
3824 #if (_CYHAL_SRSS_NUM_PLL > 6)
3825     _CYHAL_CLOCK_CREATE(PLL, 6),
3826 #endif
3827 #if (_CYHAL_SRSS_NUM_PLL > 7)
3828     _CYHAL_CLOCK_CREATE(PLL, 7),
3829 #endif
3830 #if (_CYHAL_SRSS_NUM_PLL > 8)
3831     _CYHAL_CLOCK_CREATE(PLL, 8),
3832 #endif
3833 #if (_CYHAL_SRSS_NUM_PLL > 9)
3834     _CYHAL_CLOCK_CREATE(PLL, 9),
3835 #endif
3836 #if (_CYHAL_SRSS_NUM_PLL > 10)
3837     _CYHAL_CLOCK_CREATE(PLL, 10),
3838 #endif
3839 #if (_CYHAL_SRSS_NUM_PLL > 11)
3840     _CYHAL_CLOCK_CREATE(PLL, 11),
3841 #endif
3842 #if (_CYHAL_SRSS_NUM_PLL > 12)
3843     _CYHAL_CLOCK_CREATE(PLL, 12),
3844 #endif
3845 #if (_CYHAL_SRSS_NUM_PLL > 13)
3846     _CYHAL_CLOCK_CREATE(PLL, 13),
3847 #endif
3848 #if (_CYHAL_SRSS_NUM_PLL > 14)
3849     _CYHAL_CLOCK_CREATE(PLL, 14),
3850 #endif
3851 };
3852 #endif
3853 #endif
3854 
3855 #if defined(COMPONENT_CAT1B) || defined(SRSS_HT_VARIANT) && (SRSS_HT_VARIANT > 0)
3856 #if defined(COMPONENT_CAT1B)
3857 const cyhal_clock_t CYHAL_CLOCK_IHO = _CYHAL_CLOCK_CREATE(IHO, 0);
3858 #if SRSS_ECO_PRESENT
3859 const cyhal_clock_t CYHAL_CLOCK_ECO_PRESCALER = _CYHAL_CLOCK_CREATE(ECO_PRESCALER, 0);
3860 #endif
3861 #if SRSS_BACKUP_S40E_LPECO_PRESENT
3862 const cyhal_clock_t CYHAL_CLOCK_LPECO_PRESCALER = _CYHAL_CLOCK_CREATE(LPECO_PRESCALER, 0);
3863 #endif
3864 #endif
3865 
3866 #if !defined(CY_DEVICE_TVIIBE)
3867     const cyhal_clock_t CYHAL_CLOCK_PERI[CY_PERI_GROUP_NR] =
3868     {
3869         _CYHAL_CLOCK_CREATE(PERI, 0),
3870     #if (CY_PERI_GROUP_NR > 1)
3871         _CYHAL_CLOCK_CREATE(PERI, 1),
3872     #endif
3873     #if (CY_PERI_GROUP_NR > 2)
3874         _CYHAL_CLOCK_CREATE(PERI, 2),
3875     #endif
3876     #if (CY_PERI_GROUP_NR > 3)
3877         _CYHAL_CLOCK_CREATE(PERI, 3),
3878     #endif
3879     #if (CY_PERI_GROUP_NR > 4)
3880         _CYHAL_CLOCK_CREATE(PERI, 4),
3881     #endif
3882     #if (CY_PERI_GROUP_NR > 5)
3883         _CYHAL_CLOCK_CREATE(PERI, 5),
3884     #endif
3885     #if (CY_PERI_GROUP_NR > 6)
3886         _CYHAL_CLOCK_CREATE(PERI, 6),
3887     #endif
3888     #if (CY_PERI_GROUP_NR > 7)
3889         _CYHAL_CLOCK_CREATE(PERI, 7),
3890     #endif
3891     #if (CY_PERI_GROUP_NR > 8)
3892         _CYHAL_CLOCK_CREATE(PERI, 8),
3893     #endif
3894     #if (CY_PERI_GROUP_NR > 9)
3895         _CYHAL_CLOCK_CREATE(PERI, 9),
3896     #endif
3897     #if (CY_PERI_GROUP_NR > 10)
3898         _CYHAL_CLOCK_CREATE(PERI, 10),
3899     #endif
3900     #if (CY_PERI_GROUP_NR > 11)
3901         _CYHAL_CLOCK_CREATE(PERI, 11),
3902     #endif
3903     #if (CY_PERI_GROUP_NR > 12)
3904         _CYHAL_CLOCK_CREATE(PERI, 12),
3905     #endif
3906     #if (CY_PERI_GROUP_NR > 13)
3907         _CYHAL_CLOCK_CREATE(PERI, 13),
3908     #endif
3909     #if (CY_PERI_GROUP_NR > 14)
3910         _CYHAL_CLOCK_CREATE(PERI, 14),
3911     #endif
3912     #if (CY_PERI_GROUP_NR > 15)
3913         _CYHAL_CLOCK_CREATE(PERI, 15),
3914     #endif
3915     };
3916 #endif /* !defined(CY_DEVICE_TVIIBE) */
3917 
3918 #if (SRSS_NUM_PLL200M > 0)
3919 #if defined(COMPONENT_CAT1B)
3920 const cyhal_clock_t CYHAL_CLOCK_PLL[SRSS_NUM_PLL200M] =
3921 {
3922 #else
3923 const cyhal_clock_t CYHAL_CLOCK_PLL200[SRSS_NUM_PLL200M] =
3924 {
3925 #endif
3926     _CYHAL_CLOCK_CREATE(PLL200, 0),
3927 #if (SRSS_NUM_PLL200M > 1)
3928     _CYHAL_CLOCK_CREATE(PLL200, 1),
3929 #endif
3930 #if (SRSS_NUM_PLL200M > 2)
3931     _CYHAL_CLOCK_CREATE(PLL200, 2),
3932 #endif
3933 #if (SRSS_NUM_PLL200M > 3)
3934     _CYHAL_CLOCK_CREATE(PLL200, 3),
3935 #endif
3936 #if (SRSS_NUM_PLL200M > 4)
3937     _CYHAL_CLOCK_CREATE(PLL200, 4),
3938 #endif
3939 #if (SRSS_NUM_PLL200M > 5)
3940     _CYHAL_CLOCK_CREATE(PLL200, 5),
3941 #endif
3942 #if (SRSS_NUM_PLL200M > 6)
3943     _CYHAL_CLOCK_CREATE(PLL200, 6),
3944 #endif
3945 #if (SRSS_NUM_PLL200M > 7)
3946     _CYHAL_CLOCK_CREATE(PLL200, 7),
3947 #endif
3948 #if (SRSS_NUM_PLL200M > 8)
3949     _CYHAL_CLOCK_CREATE(PLL200, 8),
3950 #endif
3951 #if (SRSS_NUM_PLL200M > 9)
3952     _CYHAL_CLOCK_CREATE(PLL200, 9),
3953 #endif
3954 #if (SRSS_NUM_PLL200M > 10)
3955     _CYHAL_CLOCK_CREATE(PLL200, 10),
3956 #endif
3957 #if (SRSS_NUM_PLL200M > 11)
3958     _CYHAL_CLOCK_CREATE(PLL200, 11),
3959 #endif
3960 #if (SRSS_NUM_PLL200M > 12)
3961     _CYHAL_CLOCK_CREATE(PLL200, 12),
3962 #endif
3963 #if (SRSS_NUM_PLL200M > 13)
3964     _CYHAL_CLOCK_CREATE(PLL200, 13),
3965 #endif
3966 #if (SRSS_NUM_PLL200M > 14)
3967     _CYHAL_CLOCK_CREATE(PLL200, 14),
3968 #endif
3969 };
3970 #endif
3971 
3972 #if (SRSS_NUM_PLL400M > 0)
3973 #if defined(COMPONENT_CAT1B)
3974 const cyhal_clock_t CYHAL_CLOCK_PLL[SRSS_NUM_PLL400M] =
3975 {
3976 #else
3977 const cyhal_clock_t CYHAL_CLOCK_PLL400[SRSS_NUM_PLL400M] =
3978 {
3979 #endif
3980     _CYHAL_CLOCK_CREATE(PLL400, 0),
3981 #if (SRSS_NUM_PLL400M > 1)
3982     _CYHAL_CLOCK_CREATE(PLL400, 1),
3983 #endif
3984 #if (SRSS_NUM_PLL400M > 2)
3985     _CYHAL_CLOCK_CREATE(PLL400, 2),
3986 #endif
3987 #if (SRSS_NUM_PLL400M > 3)
3988     _CYHAL_CLOCK_CREATE(PLL400, 3),
3989 #endif
3990 #if (SRSS_NUM_PLL400M > 4)
3991     _CYHAL_CLOCK_CREATE(PLL400, 4),
3992 #endif
3993 #if (SRSS_NUM_PLL400M > 5)
3994     _CYHAL_CLOCK_CREATE(PLL400, 5),
3995 #endif
3996 #if (SRSS_NUM_PLL400M > 6)
3997     _CYHAL_CLOCK_CREATE(PLL400, 6),
3998 #endif
3999 #if (SRSS_NUM_PLL400M > 7)
4000     _CYHAL_CLOCK_CREATE(PLL400, 7),
4001 #endif
4002 #if (SRSS_NUM_PLL400M > 8)
4003     _CYHAL_CLOCK_CREATE(PLL400, 8),
4004 #endif
4005 #if (SRSS_NUM_PLL400M > 9)
4006     _CYHAL_CLOCK_CREATE(PLL400, 9),
4007 #endif
4008 #if (SRSS_NUM_PLL400M > 10)
4009     _CYHAL_CLOCK_CREATE(PLL400, 10),
4010 #endif
4011 #if (SRSS_NUM_PLL400M > 11)
4012     _CYHAL_CLOCK_CREATE(PLL400, 11),
4013 #endif
4014 #if (SRSS_NUM_PLL400M > 12)
4015     _CYHAL_CLOCK_CREATE(PLL400, 12),
4016 #endif
4017 #if (SRSS_NUM_PLL400M > 13)
4018     _CYHAL_CLOCK_CREATE(PLL400, 13),
4019 #endif
4020 #if (SRSS_NUM_PLL400M > 14)
4021     _CYHAL_CLOCK_CREATE(PLL400, 14),
4022 #endif
4023 };
4024 #endif
4025 #endif
4026 
4027 #if defined(COMPONENT_CAT1D)
4028 const cyhal_clock_t CYHAL_CLOCK_DPLL250[SRSS_NUM_DPLL250M] =
4029 {
4030 #if (SRSS_NUM_DPLL250M > 0)
4031     _CYHAL_CLOCK_CREATE(DPLL250, 0),
4032 #endif
4033 #if (SRSS_NUM_DPLL250M > 1)
4034     _CYHAL_CLOCK_CREATE(DPLL250, 1),
4035 #endif
4036 #if (SRSS_NUM_DPLL250M > 2)
4037     _CYHAL_CLOCK_CREATE(DPLL250, 2),
4038 #endif
4039 #if (SRSS_NUM_DPLL250M > 3)
4040     _CYHAL_CLOCK_CREATE(DPLL250, 4),
4041 #endif
4042 #if (SRSS_NUM_DPLL250M > 4)
4043     _CYHAL_CLOCK_CREATE(DPLL250, 4),
4044 #endif
4045 };
4046 const cyhal_clock_t CYHAL_CLOCK_DPLL500[SRSS_NUM_DPLL500M] =
4047 {
4048 #if (SRSS_NUM_DPLL500M > 0)
4049     _CYHAL_CLOCK_CREATE(DPLL500, 0),
4050 #endif
4051 #if (SRSS_NUM_DPLL500M > 1)
4052     _CYHAL_CLOCK_CREATE(DPLL500, 1),
4053 #endif
4054 #if (SRSS_NUM_DPLL500M > 2)
4055     _CYHAL_CLOCK_CREATE(DPLL500, 2),
4056 #endif
4057 #if (SRSS_NUM_DPLL500M > 3)
4058     _CYHAL_CLOCK_CREATE(DPLL500, 4),
4059 #endif
4060 #if (SRSS_NUM_DPLL500M > 4)
4061     _CYHAL_CLOCK_CREATE(DPLL500, 4),
4062 #endif
4063 };
4064 #endif /* defined(COMPONENT_CAT1D) */
4065 
4066 
4067 
4068 /******************************************************************************
4069  **************************** Public API (clocks) *****************************
4070  *****************************************************************************/
4071 
_cyhal_clock_allocate_channel(cyhal_clock_t * clock,cyhal_clock_block_t block,const void * funcs)4072 cy_rslt_t _cyhal_clock_allocate_channel(cyhal_clock_t *clock, cyhal_clock_block_t block, const void* funcs)
4073 {
4074     uint8_t maxChannels = (uint8_t)_cyhal_utils_get_clock_count(block);
4075     for (uint8_t i = 0; i < maxChannels; i++)
4076     {
4077         cyhal_resource_inst_t clock_resource = { CYHAL_RSC_CLOCK, block, i };
4078         if (CY_RSLT_SUCCESS == cyhal_hwmgr_reserve(&clock_resource))
4079         {
4080             clock->block = block;
4081             clock->channel = i;
4082             clock->reserved = true;
4083             clock->funcs = funcs;
4084             return CY_RSLT_SUCCESS;
4085         }
4086     }
4087     return CYHAL_HWMGR_RSLT_ERR_NONE_FREE;
4088 }
4089 
cyhal_clock_get(cyhal_clock_t * clock,const cyhal_resource_inst_t * resource)4090 cy_rslt_t cyhal_clock_get(cyhal_clock_t *clock, const cyhal_resource_inst_t *resource)
4091 {
4092     CY_ASSERT(NULL != clock);
4093     CY_ASSERT(NULL != resource);
4094     CY_ASSERT(CYHAL_RSC_CLOCK == resource->type);
4095 
4096     clock->block = (cyhal_clock_block_t)resource->block_num;
4097     clock->channel = resource->channel_num;
4098     clock->reserved = false;
4099     clock->funcs = _cyhal_clock_get_funcs_all((cyhal_clock_block_t)resource->block_num);
4100 
4101     return CY_RSLT_SUCCESS;
4102 }
4103 
cyhal_clock_reserve(cyhal_clock_t * clock,const cyhal_clock_t * clock_)4104 cy_rslt_t cyhal_clock_reserve(cyhal_clock_t *clock, const cyhal_clock_t *clock_)
4105 {
4106     CY_ASSERT(NULL != clock);
4107     CY_ASSERT(NULL != clock_);
4108 
4109     cyhal_resource_inst_t clock_resource = { CYHAL_RSC_CLOCK, clock_->block, clock_->channel };
4110     cy_rslt_t rslt = cyhal_hwmgr_reserve(&clock_resource);
4111     if (CY_RSLT_SUCCESS == rslt)
4112     {
4113         memcpy(clock, clock_, sizeof(cyhal_clock_t));
4114         clock->reserved = true;
4115     }
4116     return rslt;
4117 }
4118 
cyhal_clock_get_features(const cyhal_clock_t * clock)4119 cyhal_clock_feature_t cyhal_clock_get_features(const cyhal_clock_t *clock)
4120 {
4121     CY_ASSERT(NULL != clock);
4122 
4123     if (clock->block == CYHAL_CLOCK_BLOCK_HF)
4124     {
4125         return (clock->channel == 0)    // HF0 cannot be disabled
4126             ? (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_SOURCE | CYHAL_CLOCK_FEATURE_DIVIDER)
4127             : (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_ENABLE | CYHAL_CLOCK_FEATURE_SOURCE | CYHAL_CLOCK_FEATURE_DIVIDER);
4128     }
4129     else if (clock->block < 4 * _CYHAL_CLOCK_PERI_GROUPS)
4130         return (cyhal_clock_feature_t)(CYHAL_CLOCK_FEATURE_ENABLE | CYHAL_CLOCK_FEATURE_DIVIDER | CYHAL_CLOCK_FEATURE_FREQUENCY);
4131     else
4132         return ((cyhal_clock_funcs_t*)clock->funcs)->features;
4133 }
4134 
cyhal_clock_is_enabled(const cyhal_clock_t * clock)4135 bool cyhal_clock_is_enabled(const cyhal_clock_t *clock)
4136 {
4137     CY_ASSERT(NULL != clock);
4138 
4139     if (clock->block == CYHAL_CLOCK_BLOCK_HF)
4140         return _cyhal_clock_is_enabled_hf(clock);
4141     else if (clock->block < 4 * _CYHAL_CLOCK_PERI_GROUPS)
4142         return _cyhal_clock_is_enabled_peripheral(clock);
4143     else
4144         return ((cyhal_clock_funcs_t*)clock->funcs)->is_enabled(clock);
4145 }
4146 
cyhal_clock_set_enabled(cyhal_clock_t * clock,bool enabled,bool wait_for_lock)4147 cy_rslt_t cyhal_clock_set_enabled(cyhal_clock_t *clock, bool enabled, bool wait_for_lock)
4148 {
4149     CY_ASSERT(NULL != clock);
4150 
4151     if (clock->block == CYHAL_CLOCK_BLOCK_HF)
4152         return _cyhal_clock_set_enabled_hf(clock, enabled, wait_for_lock);
4153     else if (clock->block < 4 * _CYHAL_CLOCK_PERI_GROUPS)
4154         return _cyhal_clock_set_enabled_peripheral(clock, enabled, wait_for_lock);
4155     else
4156         return ((cyhal_clock_funcs_t*)clock->funcs)->set_enabled(clock, enabled, wait_for_lock);
4157 }
4158 
cyhal_clock_get_frequency(const cyhal_clock_t * clock)4159 uint32_t cyhal_clock_get_frequency(const cyhal_clock_t *clock)
4160 {
4161     CY_ASSERT(NULL != clock);
4162 
4163     if (cyhal_clock_is_enabled(clock))
4164     {
4165         if (clock->block == CYHAL_CLOCK_BLOCK_HF)
4166             return _cyhal_clock_get_frequency_hf(clock);
4167         else if (clock->block < 4 * _CYHAL_CLOCK_PERI_GROUPS)
4168             return _cyhal_clock_get_frequency_peripheral(clock);
4169         else
4170             return ((cyhal_clock_funcs_t*)clock->funcs)->get_frequency(clock);
4171     }
4172     return 0;
4173 }
4174 
cyhal_clock_set_frequency(cyhal_clock_t * clock,uint32_t hz,const cyhal_clock_tolerance_t * tolerance)4175 cy_rslt_t cyhal_clock_set_frequency(cyhal_clock_t *clock, uint32_t hz, const cyhal_clock_tolerance_t *tolerance)
4176 {
4177     CY_ASSERT(NULL != clock);
4178 
4179     if (clock->block == CYHAL_CLOCK_BLOCK_HF)
4180         return _cyhal_clock_set_frequency_unsupported(clock, hz, tolerance);
4181     else if (clock->block < 4 * _CYHAL_CLOCK_PERI_GROUPS)
4182         return _cyhal_clock_set_frequency_peripheral(clock, hz, tolerance);
4183     else
4184         return ((cyhal_clock_funcs_t*)clock->funcs)->set_frequency(clock, hz, tolerance);
4185 }
4186 
cyhal_clock_set_divider(cyhal_clock_t * clock,uint32_t divider)4187 cy_rslt_t cyhal_clock_set_divider(cyhal_clock_t *clock, uint32_t divider)
4188 {
4189     CY_ASSERT(NULL != clock);
4190 
4191     if (clock->block == CYHAL_CLOCK_BLOCK_HF)
4192         return _cyhal_clock_set_divider_hf(clock, divider);
4193     else if (clock->block < 4 * _CYHAL_CLOCK_PERI_GROUPS)
4194         return _cyhal_clock_set_divider_peripheral(clock, divider);
4195     else
4196         return ((cyhal_clock_funcs_t*)clock->funcs)->set_divider(clock, divider);
4197 }
4198 
cyhal_clock_get_sources(const cyhal_clock_t * clock,const cyhal_resource_inst_t ** sources[],uint32_t * count)4199 cy_rslt_t cyhal_clock_get_sources(const cyhal_clock_t *clock, const cyhal_resource_inst_t **sources[], uint32_t *count)
4200 {
4201     CY_ASSERT(NULL != clock);
4202 
4203     if (clock->block == CYHAL_CLOCK_BLOCK_HF)
4204         return _cyhal_clock_get_sources_hf(clock, sources, count);
4205     else if (clock->block < 4 * _CYHAL_CLOCK_PERI_GROUPS)
4206         return _cyhal_clock_get_sources_peripheral(clock, sources, count);
4207     else
4208         return ((cyhal_clock_funcs_t*)clock->funcs)->get_sources(clock, sources, count);
4209 }
4210 
cyhal_clock_set_source(cyhal_clock_t * clock,const cyhal_clock_t * source)4211 cy_rslt_t cyhal_clock_set_source(cyhal_clock_t *clock, const cyhal_clock_t *source)
4212 {
4213     CY_ASSERT(NULL != clock && NULL != source);
4214 
4215     if (clock->block == CYHAL_CLOCK_BLOCK_HF)
4216         return _cyhal_clock_set_source_hf(clock, source);
4217     else if (clock->block < 4 * _CYHAL_CLOCK_PERI_GROUPS)
4218         return _cyhal_clock_set_source_unsupported(clock, source);
4219     else
4220         return ((cyhal_clock_funcs_t*)clock->funcs)->set_source(clock, source);
4221 }
4222 
cyhal_clock_free(cyhal_clock_t * clock)4223 void cyhal_clock_free(cyhal_clock_t *clock)
4224 {
4225     CY_ASSERT(NULL != clock);
4226     CY_ASSERT(clock->reserved);
4227 
4228     cyhal_resource_inst_t rsc = { CYHAL_RSC_CLOCK, clock->block, clock->channel };
4229     cyhal_hwmgr_free(&rsc);
4230     clock->reserved = false;
4231 }
4232 
4233 #if defined(__cplusplus)
4234 }
4235 #endif
4236 
4237 #endif // CYHAL_DRIVER_AVAILABLE_CLOCK
4238