1 /*
2 * Copyright (c) 2020 - 2024 Renesas Electronics Corporation and/or its affiliates
3 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 */
6 
7 /***********************************************************************************************************************
8  * Includes   <System Includes> , "Project Includes"
9  **********************************************************************************************************************/
10 #include "bsp_api.h"
11 
12 /***********************************************************************************************************************
13  * Macro definitions
14  **********************************************************************************************************************/
15 
16 /***********************************************************************************************************************
17  * Typedef definitions
18  **********************************************************************************************************************/
19 
20 /***********************************************************************************************************************
21  * Exported global variables (to be accessed by other files)
22  **********************************************************************************************************************/
23 
24 #if (1 == BSP_FEATURE_BSP_IRQ_GPT_SEL_SUPPORTED)
25 
26 /* Pointer to control structure table. */
27 void ** gp_bsp_gpt_combined_ctrl_table[BSP_IRQ_GPT_COMBINED_GROUP_NUM] =
28 {
29     NULL,                              /* Pointer to Group 0 control structure table.  (Use NS_GPT_INTSTAT0) */
30     NULL,                              /* Pointer to Group 1 control structure table.  (Use NS_GPT_INTSTAT1) */
31     NULL,                              /* Pointer to Group 2 control structure table.  (Use NS_GPT_INTSTAT2) */
32     NULL,                              /* Pointer to Group 3 control structure table.  (Use NS_GPT_INTSTAT3) */
33     NULL,                              /* Pointer to Group 4 control structure table.  (Use NS_GPT_INTSTAT4) */
34     NULL,                              /* Pointer to Group 5 control structure table.  (Use NS_GPT_INTSTAT5) */
35     NULL,                              /* Pointer to Group 6 control structure table.  (Use NS_GPT_INTSTAT6) */
36     NULL,                              /* Pointer to Group 7 control structure table.  (Use NS_GPT_INTSTAT7) */
37     NULL,                              /* Pointer to Group 8 control structure table.  (Use NS_GPT_INTSTAT8) */
38     NULL,                              /* Pointer to Group 9 control structure table.  (Use NS_GPT_INTSTAT9) */
39     NULL,                              /* Pointer to Group 10 control structure table. (Use NS_GPT_INTSTAT10) */
40     NULL,                              /* Pointer to Group 11 control structure table. (Use NS_GPT_INTSTAT11) */
41     NULL,                              /* Pointer to Group 12 control structure table. (Use NS_GPT_INTSTAT12) */
42     NULL,                              /* Pointer to Group 13 control structure table. (Use NS_GPT_INTSTAT13) */
43     NULL,                              /* Pointer to Group 14 control structure table. (Use NS_GPT_INTSTAT14) */
44     NULL,                              /* Pointer to Group 15 control structure table. (Use NS_GPT_INTSTAT15) */
45     NULL,                              /* Pointer to Group 16 control structure table. (Use NS_GPT_INTSTAT16) */
46     NULL,                              /* Pointer to Group 17 control structure table. (Use NS_GPT_INTSTAT17) */
47     NULL,                              /* Pointer to Group 18 control structure table. (Use NS_GPT_INTSTAT18) */
48     NULL,                              /* Pointer to Group 19 control structure table. (Use NS_GPT_INTSTAT19) */
49     NULL,                              /* Pointer to Group 20 control structure table. (Use NS_GPT_INTSTAT20) */
50     NULL,                              /* Pointer to Group 21 control structure table. (Use NS_GPT_INTSTAT21) */
51     NULL,                              /* Pointer to Group 22 control structure table. (Use NS_GPT_INTSTAT22) */
52     NULL,                              /* Pointer to Group 23 control structure table. (Use NS_GPT_INTSTAT23) */
53     NULL,                              /* Pointer to Group 24 control structure table. (Use NS_GPT_INTSTAT24) */
54     NULL,                              /* Pointer to Group 25 control structure table. (Use NS_GPT_INTSTAT25) */
55     NULL,                              /* Pointer to Group 26 control structure table. (Use S_GPT_INTSTAT0) */
56     NULL,                              /* Pointer to Group 27 control structure table. (Use S_GPT_INTSTAT1) */
57 };
58 
59 /* Pointer to interrupt handler table. */
60 fsp_vector_t * gp_bsp_gpt_combined_isr_table[BSP_IRQ_GPT_COMBINED_GROUP_NUM] =
61 {
62     NULL,                              /* Pointer to Group 0 interrupt handler table.  (Use NS_GPT_INTSTAT0) */
63     NULL,                              /* Pointer to Group 1 interrupt handler table.  (Use NS_GPT_INTSTAT1) */
64     NULL,                              /* Pointer to Group 2 interrupt handler table.  (Use NS_GPT_INTSTAT2) */
65     NULL,                              /* Pointer to Group 3 interrupt handler table.  (Use NS_GPT_INTSTAT3) */
66     NULL,                              /* Pointer to Group 4 interrupt handler table.  (Use NS_GPT_INTSTAT4) */
67     NULL,                              /* Pointer to Group 5 interrupt handler table.  (Use NS_GPT_INTSTAT5) */
68     NULL,                              /* Pointer to Group 6 interrupt handler table.  (Use NS_GPT_INTSTAT6) */
69     NULL,                              /* Pointer to Group 7 interrupt handler table.  (Use NS_GPT_INTSTAT7) */
70     NULL,                              /* Pointer to Group 8 interrupt handler table.  (Use NS_GPT_INTSTAT8) */
71     NULL,                              /* Pointer to Group 9 interrupt handler table.  (Use NS_GPT_INTSTAT9) */
72     NULL,                              /* Pointer to Group 10 interrupt handler table. (Use NS_GPT_INTSTAT10) */
73     NULL,                              /* Pointer to Group 11 interrupt handler table. (Use NS_GPT_INTSTAT11) */
74     NULL,                              /* Pointer to Group 12 interrupt handler table. (Use NS_GPT_INTSTAT12) */
75     NULL,                              /* Pointer to Group 13 interrupt handler table. (Use NS_GPT_INTSTAT13) */
76     NULL,                              /* Pointer to Group 14 interrupt handler table. (Use NS_GPT_INTSTAT14) */
77     NULL,                              /* Pointer to Group 15 interrupt handler table. (Use NS_GPT_INTSTAT15) */
78     NULL,                              /* Pointer to Group 16 interrupt handler table. (Use NS_GPT_INTSTAT16) */
79     NULL,                              /* Pointer to Group 17 interrupt handler table. (Use NS_GPT_INTSTAT17) */
80     NULL,                              /* Pointer to Group 18 interrupt handler table. (Use NS_GPT_INTSTAT18) */
81     NULL,                              /* Pointer to Group 19 interrupt handler table. (Use NS_GPT_INTSTAT19) */
82     NULL,                              /* Pointer to Group 20 interrupt handler table. (Use NS_GPT_INTSTAT20) */
83     NULL,                              /* Pointer to Group 21 interrupt handler table. (Use NS_GPT_INTSTAT21) */
84     NULL,                              /* Pointer to Group 22 interrupt handler table. (Use NS_GPT_INTSTAT22) */
85     NULL,                              /* Pointer to Group 23 interrupt handler table. (Use NS_GPT_INTSTAT23) */
86     NULL,                              /* Pointer to Group 24 interrupt handler table. (Use NS_GPT_INTSTAT24) */
87     NULL,                              /* Pointer to Group 25 interrupt handler table. (Use NS_GPT_INTSTAT25) */
88     NULL,                              /* Pointer to Group 26 control structure table. (Use S_GPT_INTSTAT0) */
89     NULL,                              /* Pointer to Group 27 control structure table. (Use S_GPT_INTSTAT1) */
90 };
91 
92 #endif
93 
94 /***********************************************************************************************************************
95  * Private global variables and functions
96  **********************************************************************************************************************/
97 
98 /*******************************************************************************************************************//**
99  * Initialize interrupt controller.
100  *
101  * @retval       None
102  **********************************************************************************************************************/
bsp_irq_cfg(void)103 void bsp_irq_cfg (void)
104 {
105     bsp_irq_core_cfg();
106 }
107 
108 #if (1 == BSP_FEATURE_BSP_IRQ_GPT_SEL_SUPPORTED)
109 
110 /*******************************************************************************************************************//**
111  * Get GPT_INT channel number.
112  *
113  * @param[in]   irq     IRQ number
114  *
115  * @return      GPT_INT channel number.
116  **********************************************************************************************************************/
bsp_prv_irq_gpt_channel_get(IRQn_Type irq)117 uint32_t bsp_prv_irq_gpt_channel_get (IRQn_Type irq)
118 {
119     return ((uint32_t) irq - BSP_IRQ_GPT_EVENT_NUM_BASE) / BSP_IRQ_GPT_INT_NUM_MAX;
120 }
121 
122 /*******************************************************************************************************************//**
123  * Get GPT_INT register number.
124  *
125  * @param[in]   channel     GPT_INT channel number
126  *
127  * @return      GPT_INT register number.
128  **********************************************************************************************************************/
bsp_prv_irq_gpt_reg_num_get(uint32_t channel)129 uint32_t bsp_prv_irq_gpt_reg_num_get (uint32_t channel)
130 {
131     return (channel % BSP_FEATURE_GPT_SAFETY_BASE_CHANNEL) / BSP_IRQ_GPT_REGISTER_DIVISION;
132 }
133 
134 /*******************************************************************************************************************//**
135  * Get bit shift value of the GPT_INTSELn register.
136  *
137  * @param[in]   irq         IRQ number
138  * @param[in]   channel     GPT_INT channel number
139  *
140  * @return      Bit shift value.
141  **********************************************************************************************************************/
bsp_prv_irq_gpt_selected_shift_num_get(IRQn_Type irq,uint32_t channel)142 uint32_t bsp_prv_irq_gpt_selected_shift_num_get (IRQn_Type irq, uint32_t channel)
143 {
144     uint32_t irqdiff = (uint32_t) irq - BSP_IRQ_GPT_EVENT_NUM_BASE;
145 
146     return channel % BSP_IRQ_GPT_REGISTER_DIVISION ?
147            BSP_IRQ_GPT_SELECTED_INTERVAL * (irqdiff % BSP_IRQ_GPT_INT_NUM_MAX) + BSP_IRQ_GPT_IY_SHIFT_NUM :
148            BSP_IRQ_GPT_SELECTED_INTERVAL * (irqdiff % BSP_IRQ_GPT_INT_NUM_MAX) + BSP_IRQ_GPT_IX_SHIFT_NUM;
149 }
150 
151 /*******************************************************************************************************************//**
152  * Get GPT_INT table number.
153  *
154  * @param[in]   channel     GPT_INT channel number
155  *
156  * @return      GPT_INT table number.
157  **********************************************************************************************************************/
bsp_prv_irq_gpt_combined_table_num_get(uint32_t channel)158 uint32_t bsp_prv_irq_gpt_combined_table_num_get (uint32_t channel)
159 {
160     return (channel % BSP_FEATURE_GPT_CHANNEL) / BSP_IRQ_GPT_REGISTER_DIVISION;
161 }
162 
163 /*******************************************************************************************************************//**
164  * Allocate memory for 'groupIndex'th control structure table.
165  *
166  * @param[in]   groupIndex         Register number
167  *
168  * @return      Allocated memory address
169  **********************************************************************************************************************/
bsp_prv_irq_gpt_combined_ctrl_table_allocate(uint32_t groupIndex)170 void * bsp_prv_irq_gpt_combined_ctrl_table_allocate (uint32_t groupIndex)
171 {
172     /* Allocate memory for 'groupIndex'th control structure table. */
173     gp_bsp_gpt_combined_ctrl_table[groupIndex] =
174         bsp_prv_malloc(BSP_IRQ_GPT_COMBINED_EVENT_NUM_PER_GROUP * sizeof(uintptr_t));
175     if (NULL != gp_bsp_gpt_combined_ctrl_table[groupIndex])
176     {
177         /* Set initial value at malloc area. */
178         for (uint32_t elementIndex = 0U; elementIndex < BSP_IRQ_GPT_COMBINED_EVENT_NUM_PER_GROUP; elementIndex++)
179         {
180             gp_bsp_gpt_combined_ctrl_table[groupIndex][elementIndex] = NULL;
181         }
182     }
183 
184     return gp_bsp_gpt_combined_ctrl_table[groupIndex];
185 }
186 
187 /*******************************************************************************************************************//**
188  * Allocate memory for 'groupIndex'th interrupt handler table.
189  *
190  * @param[in]   groupIndex         Register number
191  *
192  * @return      Allocated memory address
193  **********************************************************************************************************************/
bsp_prv_irq_gpt_combined_isr_table_allocate(uint32_t groupIndex)194 void * bsp_prv_irq_gpt_combined_isr_table_allocate (uint32_t groupIndex)
195 {
196     /* Allocate memory for 'groupIndex'th structure table. */
197     gp_bsp_gpt_combined_isr_table[groupIndex] =
198         bsp_prv_malloc(BSP_IRQ_GPT_COMBINED_EVENT_NUM_PER_GROUP * sizeof(uintptr_t));
199     if (NULL != gp_bsp_gpt_combined_isr_table[groupIndex])
200     {
201         /* Set initial value at malloc area. */
202         for (uint32_t elementIndex = 0U; elementIndex < BSP_IRQ_GPT_COMBINED_EVENT_NUM_PER_GROUP; elementIndex++)
203         {
204             gp_bsp_gpt_combined_isr_table[groupIndex][elementIndex] = NULL;
205         }
206     }
207 
208     return gp_bsp_gpt_combined_isr_table[groupIndex];
209 }
210 
211 /*******************************************************************************************************************//**
212  * Get bit shift value of GPT_INTMSKn, GPT_INTCLRn and GPT_INTSTATn registers.
213  *
214  * @param[in]   channel       GPT_INT channel number
215  * @param[in]   event_source  Define the bit shift values ​​of GPT_INTMSKn, GPT_INTCLRn and GPT_INTSTATn as an enum.
216  *
217  * @return      Bit shift value.
218  **********************************************************************************************************************/
bsp_prv_irq_gpt_combined_shift_num_get(uint32_t channel,bsp_irq_gpt_combined_event_t event_source)219 uint32_t bsp_prv_irq_gpt_combined_shift_num_get (uint32_t channel, bsp_irq_gpt_combined_event_t event_source)
220 {
221     return channel % BSP_IRQ_GPT_REGISTER_DIVISION ? (uint32_t) event_source + BSP_IRQ_GPT_IY_SHIFT_NUM :
222            (uint32_t) event_source + BSP_IRQ_GPT_IX_SHIFT_NUM;
223 }
224 
225 /*******************************************************************************************************************//**
226  * Called when a GPT combined interrupt occurs, clears the GPT/MTU3 interrupt and executes the ISR function.
227  **********************************************************************************************************************/
bsp_irq_gpt_combined_interrupt_handler(void)228 void bsp_irq_gpt_combined_interrupt_handler (void)
229 {
230     /* Save context if RTOS is used */
231     FSP_CONTEXT_SAVE;
232 
233     IRQn_Type irq = R_FSP_CurrentIrqGet();
234 
235     uint32_t gpt_intstat = R_BSP_IrqGptCombinedStatusRead(irq);
236 
237     /* Since the GPT/MTU interrupt status is divided into upper 16 bits and lower 16 bits,
238      * the bit positions are adjusted for the upper bits. */
239     if (bsp_prv_irq_gpt_channel_get(irq) % BSP_IRQ_GPT_REGISTER_DIVISION)
240     {
241         gpt_intstat >>= BSP_IRQ_GPT_IY_SHIFT_NUM;
242     }
243 
244     bsp_irq_gpt_combined_event_t event_source;
245     uint32_t next_event  = 0;
246     uint32_t event_shift = 0;
247     void   * p_context;
248     void     (* p_interrupt_handler)(void);
249 
250     while (gpt_intstat)
251     {
252         /* Scan and search for GPT and MTU3 interrupts factors one by one. */
253         next_event    = __CLZ(__RBIT(gpt_intstat));
254         gpt_intstat >>= next_event;
255         event_shift  += next_event;
256         event_source  = (bsp_irq_gpt_combined_event_t) (event_shift & BSP_IRQ_GPT_COMBINED_EVENT_ENUM_MASK);
257 
258         /* Obtains the context and interrupt handler from the table and executes interrupt processing. */
259         R_BSP_IrqGptCombinedStatusClear(irq, event_source);
260         p_context = R_BSP_IrqGptCombinedCtrlGet(irq, event_source);
261         R_FSP_IsrContextSet(irq, p_context);
262         p_interrupt_handler = R_BSP_IrqGptCombinedIsrGet(irq, event_source);
263         p_interrupt_handler();
264 
265         /* Clear the scanned flags one by one. */
266         gpt_intstat &= (uint32_t) ~(1UL);
267     }
268 
269     /* Restore context if RTOS is used */
270     FSP_CONTEXT_RESTORE;
271 }
272 
273 #endif
274