1 /*
2  * Copyright 2017-2019 NXP
3  *
4  * SPDX-License-Identifier: BSD-3-Clause
5  */
6 
7 #include "fsl_dac.h"
8 #include "fsl_clock.h"
9 
10 /* Component ID definition, used by tools. */
11 #ifndef FSL_COMPONENT_ID
12 #define FSL_COMPONENT_ID "platform.drivers.lpc_dac"
13 #endif
14 
15 /*******************************************************************************
16  * Variables
17  ******************************************************************************/
18 
19 /* Array of GPIO peripheral base address. */
20 static DAC_Type *const s_dacBases[] = DAC_BASE_PTRS;
21 
22 #if !(defined(FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL) && FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL)
23 /* Array of GPIO clock name. */
24 static const clock_ip_name_t s_dacClocks[] = DAC_CLOCKS;
25 #endif /* FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL */
26 
27 #if !(defined(FSL_FEATURE_DAC_HAS_NO_RESET) && FSL_FEATURE_DAC_HAS_NO_RESET)
28 static const reset_ip_name_t s_dacResets[] = DAC_RSTS_N;
29 #endif
30 /*******************************************************************************
31  * Prototypes
32  ******************************************************************************/
33 
34 /*!
35  * @brief Gets the DAC instance according to the DAC base.
36  *
37  * @param base DAC peripheral base pointer.
38  * @retval DAC instance.
39  */
40 static uint32_t DAC_GetInstance(DAC_Type *base);
41 
42 /*******************************************************************************
43  * Code
44  ******************************************************************************/
45 
DAC_GetInstance(DAC_Type * base)46 static uint32_t DAC_GetInstance(DAC_Type *base)
47 {
48     uint32_t instance;
49 
50     /* Find the instance index from base address mappings. */
51     for (instance = 0; instance < ARRAY_SIZE(s_dacBases); instance++)
52     {
53         if (s_dacBases[instance] == base)
54         {
55             break;
56         }
57     }
58 
59     assert(instance < ARRAY_SIZE(s_dacBases));
60 
61     return instance;
62 }
63 
64 /*!
65  * brief Initialize the DAC module.
66  *
67  * param base DAC peripheral base address.
68  * param config The pointer to configuration structure. Please refer to "dac_config_t" structure.
69  */
DAC_Init(DAC_Type * base,const dac_config_t * config)70 void DAC_Init(DAC_Type *base, const dac_config_t *config)
71 {
72     assert(config != NULL);
73 
74 #if !(defined(FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL) && FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL)
75     /* Enable clock. */
76     CLOCK_EnableClock(s_dacClocks[DAC_GetInstance(base)]);
77 #endif /* FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL */
78 
79 #if !(defined(FSL_FEATURE_DAC_HAS_NO_RESET) && FSL_FEATURE_DAC_HAS_NO_RESET)
80     /* Reset the DAC module */
81     RESET_PeripheralReset(s_dacResets[DAC_GetInstance(base)]);
82 #endif
83 
84     base->CR &= ~DAC_CR_BIAS_MASK;
85     base->CR |= DAC_CR_BIAS(config->settlingTime);
86 }
87 
88 /*!
89  * brief De-Initialize the DAC module.
90  *
91  * param base DAC peripheral base address.
92  */
DAC_Deinit(DAC_Type * base)93 void DAC_Deinit(DAC_Type *base)
94 {
95 #if !(defined(FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL) && FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL)
96     /* Disable the clock. */
97     CLOCK_DisableClock(s_dacClocks[DAC_GetInstance(base)]);
98 #endif /* FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL */
99 }
100 
101 /*!
102  * brief Initializes the DAC user configuration structure.
103  *
104  * This function initializes the user configuration structure to a default value. The default values are as follows.
105  * code
106  *   config->settlingTime = kDAC_SettlingTimeIs1us;
107  * endcode
108  * param config Pointer to the configuration structure. See "dac_config_t".
109  */
DAC_GetDefaultConfig(dac_config_t * config)110 void DAC_GetDefaultConfig(dac_config_t *config)
111 {
112     assert(config != NULL);
113 
114     /* Initializes the configure structure to zero. */
115     (void)memset(config, 0, sizeof(*config));
116 
117     config->settlingTime = kDAC_SettlingTimeIs1us;
118 }
119 
120 /*!
121  * brief Enable/Diable double-buffering feature. Notice: Disabling the double-buffering feature will disable counter
122  * opreation.
123  *        If double-buffering feature is disabled, any writes to the CR address will go directly to the CR register.
124  *        If double-buffering feature is enabled, any write to the CR register will only load the pre-buffer,
125  *        which shares its register address with the CR register. The CR itself will be loaded from the pre-buffer
126  *        whenever the counter reaches zero and the DMA request is set.
127  *
128  * param base DAC peripheral base address.
129  * param enable Enable or disable the feature.
130  */
DAC_EnableDoubleBuffering(DAC_Type * base,bool enable)131 void DAC_EnableDoubleBuffering(DAC_Type *base, bool enable)
132 {
133     if (enable)
134     {
135         base->CTRL |= DAC_CTRL_DBLBUF_ENA_MASK;
136         base->CTRL |= DAC_CTRL_CNT_ENA_MASK;
137     }
138     else
139     {
140         base->CTRL &= ~DAC_CTRL_DBLBUF_ENA_MASK;
141         base->CTRL &= ~DAC_CTRL_CNT_ENA_MASK;
142     }
143 }
144 
145 /*!
146  * brief Write DAC output value into CR register or pre-buffer. The DAC output voltage is VALUE*((VREFP)/1024).
147  *
148  * param base DAC peripheral base address.
149  * param value Setting the value for items in the buffer. 10-bits are available.
150  */
DAC_SetBufferValue(DAC_Type * base,uint32_t value)151 void DAC_SetBufferValue(DAC_Type *base, uint32_t value)
152 {
153     assert(value < 1024U);
154 
155     base->CR = (base->CR & ~DAC_CR_VALUE_MASK) | DAC_CR_VALUE(value);
156 }
157 
158 /*!
159  * brief Write DAC counter value into CNTVAL register.
160  *        When the counter is enabled bit, the 16-bit counter will begin counting down, at the rate selected by PCLK,
161  *        from the value programmed into the DACCNTVAL register. The counter is decremented Each time the counter
162  * reaches zero, the counter will be reloaded by the value of DACCNTVAL and the DMA request bit INT_DMA_REQ will be set
163  * in hardware.
164  *
165  * param base DAC peripheral basic address.
166  * param value Setting the value for items in the counter. 16-bits are available.
167  */
DAC_SetCounterValue(DAC_Type * base,uint32_t value)168 void DAC_SetCounterValue(DAC_Type *base, uint32_t value)
169 {
170     assert(value < 65536U);
171 
172     base->CNTVAL &= ~DAC_CNTVAL_VALUE_MASK;
173     base->CNTVAL |= DAC_CNTVAL_VALUE(value);
174 }
175