1 /**************************************************************************//**
2  * @file     ebi.c
3  * @version  V3.00
4  * @brief    External Bus Interface(EBI) driver source file
5  *
6  * @copyright SPDX-License-Identifier: Apache-2.0
7  * @copyright Copyright (C) 2021 Nuvoton Technology Corp. All rights reserved.
8  *****************************************************************************/
9 #include "NuMicro.h"
10 
11 
12 /** @addtogroup Standard_Driver Standard Driver
13   @{
14 */
15 
16 /** @addtogroup EBI_Driver EBI Driver
17   @{
18 */
19 
20 /** @addtogroup EBI_EXPORTED_FUNCTIONS EBI Exported Functions
21   @{
22 */
23 
24 /**
25   * @brief      Initialize EBI for specify Bank
26   *
27   * @param[in]  u32Bank             Bank number for EBI. Valid values are:
28   *                                     - \ref EBI_BANK0
29   *                                     - \ref EBI_BANK1
30   *                                     - \ref EBI_BANK2
31   * @param[in]  u32DataWidth        Data bus width. Valid values are:
32   *                                     - \ref EBI_BUSWIDTH_8BIT
33   *                                     - \ref EBI_BUSWIDTH_16BIT
34   * @param[in]  u32TimingClass      Default timing configuration. Valid values are:
35   *                                     - \ref EBI_TIMING_FASTEST
36   *                                     - \ref EBI_TIMING_VERYFAST
37   *                                     - \ref EBI_TIMING_FAST
38   *                                     - \ref EBI_TIMING_NORMAL
39   *                                     - \ref EBI_TIMING_SLOW
40   *                                     - \ref EBI_TIMING_VERYSLOW
41   *                                     - \ref EBI_TIMING_SLOWEST
42   * @param[in]  u32BusMode          Set EBI bus operate mode. Valid values are:
43   *                                     - \ref EBI_OPMODE_NORMAL
44   *                                     - \ref EBI_OPMODE_CACCESS
45   *                                     - \ref EBI_OPMODE_ADSEPARATE
46   * @param[in]  u32CSActiveLevel    CS is active High/Low. Valid values are:
47   *                                     - \ref EBI_CS_ACTIVE_HIGH
48   *                                     - \ref EBI_CS_ACTIVE_LOW
49   *
50   * @return     None
51   *
52   * @details    This function is used to open specify EBI bank with different bus width, timing setting and \n
53   *             active level of CS pin to access EBI device.
54   * @note       Write Buffer Enable(WBUFEN) and Extend Time Of ALE(TALE) are only available in EBI bank0 control register.
55   */
EBI_Open(uint32_t u32Bank,uint32_t u32DataWidth,uint32_t u32TimingClass,uint32_t u32BusMode,uint32_t u32CSActiveLevel)56 void EBI_Open(uint32_t u32Bank, uint32_t u32DataWidth, uint32_t u32TimingClass, uint32_t u32BusMode, uint32_t u32CSActiveLevel)
57 {
58     uint32_t u32Index0 = (uint32_t)&EBI->CTL0 + ((uint32_t)u32Bank * 0x10UL);
59     uint32_t u32Index1 = (uint32_t)&EBI->TCTL0 + ((uint32_t)u32Bank * 0x10UL);
60     volatile uint32_t *pu32EBICTL  = (uint32_t *)( u32Index0 );
61     volatile uint32_t *pu32EBITCTL = (uint32_t *)( u32Index1 );
62 
63     if(u32DataWidth == EBI_BUSWIDTH_8BIT)
64     {
65         *pu32EBICTL &= ~EBI_CTL_DW16_Msk;
66     }
67     else
68     {
69         *pu32EBICTL |= EBI_CTL_DW16_Msk;
70     }
71 
72     *pu32EBICTL |= u32BusMode;
73 
74     switch(u32TimingClass)
75     {
76         case EBI_TIMING_FASTEST:
77             *pu32EBICTL = (*pu32EBICTL & ~(EBI_CTL_MCLKDIV_Msk | EBI_CTL_TALE_Msk)) |
78                           (EBI_MCLKDIV_1 << EBI_CTL_MCLKDIV_Pos) |
79                           (u32CSActiveLevel << EBI_CTL_CSPOLINV_Pos) | EBI_CTL_EN_Msk;
80             *pu32EBITCTL = 0x0UL;
81             break;
82 
83         case EBI_TIMING_VERYFAST:
84             *pu32EBICTL = (*pu32EBICTL & ~(EBI_CTL_MCLKDIV_Msk | EBI_CTL_TALE_Msk)) |
85                           (EBI_MCLKDIV_1 << EBI_CTL_MCLKDIV_Pos) |
86                           (u32CSActiveLevel << EBI_CTL_CSPOLINV_Pos) | EBI_CTL_EN_Msk |
87                           (0x3U << EBI_CTL_TALE_Pos) ;
88             *pu32EBITCTL = 0x03003318UL;
89             break;
90 
91         case EBI_TIMING_FAST:
92             *pu32EBICTL = (*pu32EBICTL & ~(EBI_CTL_MCLKDIV_Msk | EBI_CTL_TALE_Msk)) |
93                           (EBI_MCLKDIV_2 << EBI_CTL_MCLKDIV_Pos) |
94                           (u32CSActiveLevel << EBI_CTL_CSPOLINV_Pos) | EBI_CTL_EN_Msk;
95             *pu32EBITCTL = 0x0UL;
96             break;
97 
98         case EBI_TIMING_NORMAL:
99             *pu32EBICTL = (*pu32EBICTL & ~(EBI_CTL_MCLKDIV_Msk | EBI_CTL_TALE_Msk)) |
100                           (EBI_MCLKDIV_2 << EBI_CTL_MCLKDIV_Pos) |
101                           (u32CSActiveLevel << EBI_CTL_CSPOLINV_Pos) | EBI_CTL_EN_Msk |
102                           (0x3UL << EBI_CTL_TALE_Pos) ;
103             *pu32EBITCTL = 0x03003318UL;
104             break;
105 
106         case EBI_TIMING_SLOW:
107             *pu32EBICTL = (*pu32EBICTL & ~(EBI_CTL_MCLKDIV_Msk | EBI_CTL_TALE_Msk)) |
108                           (EBI_MCLKDIV_2 << EBI_CTL_MCLKDIV_Pos) |
109                           (u32CSActiveLevel << EBI_CTL_CSPOLINV_Pos) | EBI_CTL_EN_Msk |
110                           (0x7UL << EBI_CTL_TALE_Pos) ;
111             *pu32EBITCTL = 0x07007738UL;
112             break;
113 
114         case EBI_TIMING_VERYSLOW:
115             *pu32EBICTL = (*pu32EBICTL & ~(EBI_CTL_MCLKDIV_Msk | EBI_CTL_TALE_Msk)) |
116                           (EBI_MCLKDIV_4 << EBI_CTL_MCLKDIV_Pos) |
117                           (u32CSActiveLevel << EBI_CTL_CSPOLINV_Pos) | EBI_CTL_EN_Msk |
118                           (0x7UL << EBI_CTL_TALE_Pos) ;
119             *pu32EBITCTL = 0x07007738UL;
120             break;
121 
122         case EBI_TIMING_SLOWEST:
123             *pu32EBICTL = (*pu32EBICTL & ~(EBI_CTL_MCLKDIV_Msk | EBI_CTL_TALE_Msk)) |
124                           (EBI_MCLKDIV_8 << EBI_CTL_MCLKDIV_Pos) |
125                           (u32CSActiveLevel << EBI_CTL_CSPOLINV_Pos) | EBI_CTL_EN_Msk |
126                           (0x7UL << EBI_CTL_TALE_Pos) ;
127             *pu32EBITCTL = 0x07007738UL;
128             break;
129 
130         default:
131             *pu32EBICTL &= ~EBI_CTL_EN_Msk;
132             break;
133     }
134 }
135 
136 /**
137   * @brief      Disable EBI on specify Bank
138   *
139   * @param[in]  u32Bank     Bank number for EBI. Valid values are:
140   *                             - \ref EBI_BANK0
141   *                             - \ref EBI_BANK1
142   *                             - \ref EBI_BANK2
143   *
144   * @return     None
145   *
146   * @details    This function is used to close specify EBI function.
147   */
EBI_Close(uint32_t u32Bank)148 void EBI_Close(uint32_t u32Bank)
149 {
150     uint32_t u32Index = (uint32_t)&EBI->CTL0 + (u32Bank * 0x10UL);
151     volatile uint32_t *pu32EBICTL = (uint32_t *)( u32Index );
152 
153     *pu32EBICTL &= ~EBI_CTL_EN_Msk;
154 }
155 
156 /**
157   * @brief      Set EBI Bus Timing for specify Bank
158   *
159   * @param[in]  u32Bank             Bank number for EBI. Valid values are:
160   *                                     - \ref EBI_BANK0
161   *                                     - \ref EBI_BANK1
162   *                                     - \ref EBI_BANK2
163   * @param[in]  u32TimingConfig     Configure EBI timing settings, includes TACC, TAHD, W2X and R2R setting.
164   * @param[in]  u32MclkDiv          Divider for MCLK. Valid values are:
165   *                                     - \ref EBI_MCLKDIV_1
166   *                                     - \ref EBI_MCLKDIV_2
167   *                                     - \ref EBI_MCLKDIV_4
168   *                                     - \ref EBI_MCLKDIV_8
169   *                                     - \ref EBI_MCLKDIV_16
170   *                                     - \ref EBI_MCLKDIV_32
171   *                                     - \ref EBI_MCLKDIV_64
172   *                                     - \ref EBI_MCLKDIV_128
173   *
174   * @return     None
175   *
176   * @details    This function is used to configure specify EBI bus timing for access EBI device.
177   */
EBI_SetBusTiming(uint32_t u32Bank,uint32_t u32TimingConfig,uint32_t u32MclkDiv)178 void EBI_SetBusTiming(uint32_t u32Bank, uint32_t u32TimingConfig, uint32_t u32MclkDiv)
179 {
180     uint32_t u32Index0 = (uint32_t)&EBI->CTL0 + (u32Bank * 0x10UL);
181     uint32_t u32Index1 = (uint32_t)&EBI->TCTL0 + (u32Bank * 0x10UL);
182     volatile uint32_t *pu32EBICTL  = (uint32_t *)( u32Index0 );
183     volatile uint32_t *pu32EBITCTL = (uint32_t *)( u32Index1 );
184 
185     *pu32EBICTL = (*pu32EBICTL & ~EBI_CTL_MCLKDIV_Msk) | (u32MclkDiv << EBI_CTL_MCLKDIV_Pos);
186     *pu32EBITCTL = u32TimingConfig;
187 }
188 
189 /**@}*/ /* end of group EBI_EXPORTED_FUNCTIONS */
190 
191 /**@}*/ /* end of group EBI_Driver */
192 
193 /**@}*/ /* end of group Standard_Driver */
194