1 /*
2 * Copyright (c) 2021 HPMicro
3 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 *
6 */
7
8 #ifndef HPM_VAD_DRV_H
9 #define HPM_VAD_DRV_H
10
11 #include "hpm_common.h"
12 #include "hpm_vad_regs.h"
13
14 /**
15 * @brief VAD driver APIs
16 * @defgroup vad_interface VAD driver APIs
17 * @ingroup io_interfaces
18 * @{
19 */
20
21 /**
22 * @brief vad event
23 */
24 #define VAD_EVENT_VAD (1U << 7)
25 #define VAD_EVENT_FIFO_DATA_AVAILABLE (1U << 6)
26 #define VAD_EVENT_MEMBUF_EMPTY (1U << 5)
27 #define VAD_EVENT_FIFO_OVERFLOW (1U << 4)
28 #define VAD_EVENT_IIR_OVERLOAD (1U << 3)
29 #define VAD_EVENT_IIR_OVERFLOW (1U << 2)
30 #define VAD_EVENT_CIC_OVERLOAD_ERROR (1U << 1)
31 #define VAD_EVENT_CIC_STA_ERROR (1U << 0)
32
33 /**
34 * @brief vad config
35 */
36 typedef struct vad_config {
37 bool enable_buffer;
38 bool enable_pdm_clock_out;
39 bool enable_two_channels;
40 uint8_t capture_delay;
41 uint8_t pdm_half_div;
42 uint8_t fifo_threshold;
43 uint8_t post_scale;
44 bool channel_polarity_high[2];
45 } vad_config_t;
46
47 #ifdef __cplusplus
48 extern "C" {
49 #endif
50
51 /**
52 * @brief set capture deplay cycle
53 *
54 * @param [in] ptr VAD base address
55 * @param [in] delay delay cycle value
56 */
vad_set_capture_delay(VAD_Type * ptr,uint8_t delay)57 static inline void vad_set_capture_delay(VAD_Type *ptr, uint8_t delay)
58 {
59 ptr->CTRL = (ptr->CTRL & ~VAD_CTRL_CAPT_DLY_MASK)
60 | VAD_CTRL_CAPT_DLY_SET(delay);
61 }
62
63 /**
64 * @brief set pdm clock hald_divider
65 *
66 * @param [in] ptr VAD base address
67 * @param [in] div divider value
68 */
vad_set_pdm_clock_half_div(VAD_Type * ptr,uint8_t div)69 static inline void vad_set_pdm_clock_half_div(VAD_Type *ptr, uint8_t div)
70 {
71 ptr->CTRL = (ptr->CTRL & ~VAD_CTRL_PDM_CLK_HFDIV_MASK)
72 | VAD_CTRL_PDM_CLK_HFDIV_SET(div);
73 }
74
75 /**
76 * @brief enable irq
77 *
78 * @param [in] ptr VAD base address
79 * @param [in] irq_mask irq mask value
80 */
vad_enable_irq(VAD_Type * ptr,uint32_t irq_mask)81 static inline void vad_enable_irq(VAD_Type *ptr, uint32_t irq_mask)
82 {
83 ptr->CTRL |= irq_mask;
84 }
85
86 /**
87 * @brief disable irq
88 *
89 * @param [in] ptr VAD base address
90 * @param [in] irq_mask irq mask value
91 */
vad_disable_irq(VAD_Type * ptr,uint32_t irq_mask)92 static inline void vad_disable_irq(VAD_Type *ptr, uint32_t irq_mask)
93 {
94 ptr->CTRL &= ~irq_mask;
95 }
96
97 /**
98 * @brief disable buffer
99 *
100 * @param [in] ptr VAD base address
101 */
vad_disable_buffer(VAD_Type * ptr)102 static inline void vad_disable_buffer(VAD_Type *ptr)
103 {
104 ptr->CTRL |= VAD_CTRL_MEMBUF_DISABLE_MASK;
105 }
106
107 /**
108 * @brief enable buffer
109 *
110 * @param [in] ptr VAD base address
111 */
vad_enable_buffer(VAD_Type * ptr)112 static inline void vad_enable_buffer(VAD_Type *ptr)
113 {
114 ptr->CTRL &= ~VAD_CTRL_MEMBUF_DISABLE_MASK;
115 }
116
117 /**
118 * @brief set fifo threshold
119 *
120 * @param [in] ptr VAD base address
121 * @param [in] threshold fifo threshold value
122 */
vad_set_fifo_threshold(VAD_Type * ptr,uint8_t threshold)123 static inline void vad_set_fifo_threshold(VAD_Type *ptr, uint8_t threshold)
124 {
125 ptr->CTRL = (ptr->CTRL & ~(VAD_CTRL_FIFO_THRSH_MASK))
126 | VAD_CTRL_FIFO_THRSH_SET(threshold);
127 }
128
129 /**
130 * @brief enable pdm clock out
131 *
132 * @param [in] ptr VAD base address
133 */
vad_enable_pdm_clock_out(VAD_Type * ptr)134 static inline void vad_enable_pdm_clock_out(VAD_Type *ptr)
135 {
136 ptr->CTRL |= VAD_CTRL_PDM_CLK_OE_MASK;
137 }
138
139 /**
140 * @brief disable pdm clock out
141 *
142 * @param [in] ptr VAD base address
143 */
vad_disable_pdm_clock_out(VAD_Type * ptr)144 static inline void vad_disable_pdm_clock_out(VAD_Type *ptr)
145 {
146 ptr->CTRL &= ~VAD_CTRL_PDM_CLK_OE_MASK;
147 }
148
149 /**
150 * @brief set pdm clock polarity
151 *
152 * @param [in] ptr VAD base address
153 * @param [in] level clock polarity
154 */
vad_set_pdm_clock_capture_level(VAD_Type * ptr,uint8_t level)155 static inline void vad_set_pdm_clock_capture_level(VAD_Type *ptr, uint8_t level)
156 {
157 ptr->CTRL = (ptr->CTRL & ~VAD_CTRL_CH_POL_MASK)
158 | VAD_CTRL_CH_POL_SET(level);
159 }
160
161 /**
162 * @brief set channel number
163 *
164 * @param [in] ptr VAD base address
165 * @param [in] two_channels:
166 * @arg true: set two channels
167 * @arg false: set one channel
168 */
vad_set_channel_number(VAD_Type * ptr,bool two_channels)169 static inline void vad_set_channel_number(VAD_Type *ptr, bool two_channels)
170 {
171 ptr->CTRL = (ptr->CTRL & ~VAD_CTRL_CHNUM_MASK)
172 | (two_channels ? VAD_CTRL_CHNUM_MASK : 0);
173 }
174
175 /**
176 * @brief get status
177 *
178 * @param [in] ptr VAD base address
179 * @retval ST register value
180 */
vad_get_status(VAD_Type * ptr)181 static inline uint32_t vad_get_status(VAD_Type *ptr)
182 {
183 return ptr->ST;
184 }
185
186 /**
187 * @brief slear status
188 *
189 * @param [in] ptr VAD base address
190 * @param [in] mask status mask value
191 */
vad_clear_status(VAD_Type * ptr,uint32_t mask)192 static inline void vad_clear_status(VAD_Type *ptr, uint32_t mask)
193 {
194 ptr->ST |= mask;
195 }
196
197 /**
198 * @brief get data
199 *
200 * @param [in] ptr VAD base address
201 * @retval OFIFO register value
202 */
vad_get_data(VAD_Type * ptr)203 static inline uint32_t vad_get_data(VAD_Type *ptr)
204 {
205 return ptr->OFIFO;
206 }
207
208 /**
209 * @brief software reset
210 *
211 * @param [in] ptr VAD base address
212 */
vad_software_reset(VAD_Type * ptr)213 static inline void vad_software_reset(VAD_Type *ptr)
214 {
215 ptr->RUN |= VAD_RUN_SFTRST_MASK;
216 ptr->RUN &= ~VAD_RUN_SFTRST_MASK;
217 }
218
219 /**
220 * @brief start
221 *
222 * @param [in] ptr VAD base address
223 */
vad_start(VAD_Type * ptr)224 static inline void vad_start(VAD_Type *ptr)
225 {
226 ptr->RUN |= VAD_RUN_VAD_EN_MASK;
227 }
228
229 /**
230 * @brief stop
231 *
232 * @param [in] ptr VAD base address
233 */
vad_stop(VAD_Type * ptr)234 static inline void vad_stop(VAD_Type *ptr)
235 {
236 ptr->RUN &= ~VAD_RUN_VAD_EN_MASK;
237 }
238
239 /**
240 * @brief check whether vad is running
241 *
242 * @param [in] ptr VAD base address
243 * @retval true if vad is running
244 */
vad_is_running(VAD_Type * ptr)245 static inline bool vad_is_running(VAD_Type *ptr)
246 {
247 return ptr->RUN & VAD_RUN_VAD_EN_MASK;
248 }
249
250 /**
251 * @brief enable fifo
252 *
253 * @param [in] ptr VAD base address
254 */
vad_enable_fifo(VAD_Type * ptr)255 static inline void vad_enable_fifo(VAD_Type *ptr)
256 {
257 ptr->OFIFO_CTRL |= VAD_OFIFO_CTRL_EN_MASK;
258 }
259
260 /**
261 * @brief disable fifo
262 *
263 * @param [in] ptr VAD base address
264 */
vad_disable_fifo(VAD_Type * ptr)265 static inline void vad_disable_fifo(VAD_Type *ptr)
266 {
267 ptr->OFIFO_CTRL &= ~VAD_OFIFO_CTRL_EN_MASK;
268 }
269
270 /**
271 * @brief get coefficient value
272 *
273 * @param [in] ptr VAD base address
274 * @param [in] index coefficient index
275 */
vad_get_coef_value(VAD_Type * ptr,uint32_t index)276 static inline uint32_t vad_get_coef_value(VAD_Type *ptr, uint32_t index)
277 {
278 return ptr->COEF[index];
279 }
280
281 /**
282 * @brief set ouptput value post scale
283 *
284 * @param [in] ptr VAD base address
285 * @param [in] post_scale post scale value
286 */
vad_set_post_scale(VAD_Type * ptr,uint8_t post_scale)287 static inline void vad_set_post_scale(VAD_Type *ptr, uint8_t post_scale)
288 {
289 ptr->CIC_CFG |= (ptr->CIC_CFG & ~VAD_CIC_CFG_POST_SCALE_MASK)
290 | VAD_CIC_CFG_POST_SCALE_SET(post_scale);
291 }
292
293 /**
294 * @brief set sampling signal amplitude limits
295 *
296 * @param [in] ptr VAD base address
297 * @param [in] high high limit
298 * @param [in] low low limit
299 */
vad_set_amplify(VAD_Type * ptr,uint16_t high,uint16_t low)300 static inline void vad_set_amplify(VAD_Type *ptr, uint16_t high, uint16_t low)
301 {
302 ptr->DEC_CTRL2 = VAD_DEC_CTRL2_AMP_HIGH_SET(high)
303 | VAD_DEC_CTRL2_AMP_LOW_SET(low);
304 }
305
306 /**
307 * @brief get default config
308 *
309 * @param [in] ptr VAD base address
310 * @param [out] config vad_config_t
311 */
312 void vad_get_default_config(VAD_Type *ptr, vad_config_t *config);
313
314 /**
315 * @brief initialization
316 *
317 * @param [in] ptr VAD base address
318 * @param [in] config vad_config_t
319 */
320 void vad_init(VAD_Type *ptr, vad_config_t *config);
321
322 /**
323 * @brief reset
324 *
325 * @param [in] ptr VAD base address
326 */
327 void vad_reset(VAD_Type *ptr);
328
329 /**
330 * @}
331 */
332
333 #ifdef __cplusplus
334 }
335 #endif
336
337 #endif /* HPM_VAD_DRV_H */
338