1 /*
2 * Copyright (c) 2015 - 2018, Nordic Semiconductor ASA
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 *
8 * 1. Redistributions of source code must retain the above copyright notice, this
9 * list of conditions and the following disclaimer.
10 *
11 * 2. Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 *
15 * 3. Neither the name of the copyright holder nor the names of its
16 * contributors may be used to endorse or promote products derived from this
17 * software without specific prior written permission.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
20 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
23 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 * POSSIBILITY OF SUCH DAMAGE.
30 */
31
32 #ifndef NRF_SAADC_H_
33 #define NRF_SAADC_H_
34
35 #include <nrfx.h>
36
37 #ifdef __cplusplus
38 extern "C" {
39 #endif
40
41 /**
42 * @defgroup nrf_saadc_hal SAADC HAL
43 * @{
44 * @ingroup nrf_saadc
45 * @brief Hardware access layer for managing the SAADC peripheral.
46 */
47
48 #define NRF_SAADC_CHANNEL_COUNT 8
49
50 /**
51 * @brief Resolution of the analog-to-digital converter.
52 */
53 typedef enum
54 {
55 NRF_SAADC_RESOLUTION_8BIT = SAADC_RESOLUTION_VAL_8bit, ///< 8 bit resolution.
56 NRF_SAADC_RESOLUTION_10BIT = SAADC_RESOLUTION_VAL_10bit, ///< 10 bit resolution.
57 NRF_SAADC_RESOLUTION_12BIT = SAADC_RESOLUTION_VAL_12bit, ///< 12 bit resolution.
58 NRF_SAADC_RESOLUTION_14BIT = SAADC_RESOLUTION_VAL_14bit ///< 14 bit resolution.
59 } nrf_saadc_resolution_t;
60
61
62 /**
63 * @brief Input selection for the analog-to-digital converter.
64 */
65 typedef enum
66 {
67 NRF_SAADC_INPUT_DISABLED = SAADC_CH_PSELP_PSELP_NC, ///< Not connected.
68 NRF_SAADC_INPUT_AIN0 = SAADC_CH_PSELP_PSELP_AnalogInput0, ///< Analog input 0 (AIN0).
69 NRF_SAADC_INPUT_AIN1 = SAADC_CH_PSELP_PSELP_AnalogInput1, ///< Analog input 1 (AIN1).
70 NRF_SAADC_INPUT_AIN2 = SAADC_CH_PSELP_PSELP_AnalogInput2, ///< Analog input 2 (AIN2).
71 NRF_SAADC_INPUT_AIN3 = SAADC_CH_PSELP_PSELP_AnalogInput3, ///< Analog input 3 (AIN3).
72 NRF_SAADC_INPUT_AIN4 = SAADC_CH_PSELP_PSELP_AnalogInput4, ///< Analog input 4 (AIN4).
73 NRF_SAADC_INPUT_AIN5 = SAADC_CH_PSELP_PSELP_AnalogInput5, ///< Analog input 5 (AIN5).
74 NRF_SAADC_INPUT_AIN6 = SAADC_CH_PSELP_PSELP_AnalogInput6, ///< Analog input 6 (AIN6).
75 NRF_SAADC_INPUT_AIN7 = SAADC_CH_PSELP_PSELP_AnalogInput7, ///< Analog input 7 (AIN7).
76 NRF_SAADC_INPUT_VDD = SAADC_CH_PSELP_PSELP_VDD ///< VDD as input.
77 } nrf_saadc_input_t;
78
79
80 /**
81 * @brief Analog-to-digital converter oversampling mode.
82 */
83 typedef enum
84 {
85 NRF_SAADC_OVERSAMPLE_DISABLED = SAADC_OVERSAMPLE_OVERSAMPLE_Bypass, ///< No oversampling.
86 NRF_SAADC_OVERSAMPLE_2X = SAADC_OVERSAMPLE_OVERSAMPLE_Over2x, ///< Oversample 2x.
87 NRF_SAADC_OVERSAMPLE_4X = SAADC_OVERSAMPLE_OVERSAMPLE_Over4x, ///< Oversample 4x.
88 NRF_SAADC_OVERSAMPLE_8X = SAADC_OVERSAMPLE_OVERSAMPLE_Over8x, ///< Oversample 8x.
89 NRF_SAADC_OVERSAMPLE_16X = SAADC_OVERSAMPLE_OVERSAMPLE_Over16x, ///< Oversample 16x.
90 NRF_SAADC_OVERSAMPLE_32X = SAADC_OVERSAMPLE_OVERSAMPLE_Over32x, ///< Oversample 32x.
91 NRF_SAADC_OVERSAMPLE_64X = SAADC_OVERSAMPLE_OVERSAMPLE_Over64x, ///< Oversample 64x.
92 NRF_SAADC_OVERSAMPLE_128X = SAADC_OVERSAMPLE_OVERSAMPLE_Over128x, ///< Oversample 128x.
93 NRF_SAADC_OVERSAMPLE_256X = SAADC_OVERSAMPLE_OVERSAMPLE_Over256x ///< Oversample 256x.
94 } nrf_saadc_oversample_t;
95
96
97 /**
98 * @brief Analog-to-digital converter channel resistor control.
99 */
100 typedef enum
101 {
102 NRF_SAADC_RESISTOR_DISABLED = SAADC_CH_CONFIG_RESP_Bypass, ///< Bypass resistor ladder.
103 NRF_SAADC_RESISTOR_PULLDOWN = SAADC_CH_CONFIG_RESP_Pulldown, ///< Pull-down to GND.
104 NRF_SAADC_RESISTOR_PULLUP = SAADC_CH_CONFIG_RESP_Pullup, ///< Pull-up to VDD.
105 NRF_SAADC_RESISTOR_VDD1_2 = SAADC_CH_CONFIG_RESP_VDD1_2 ///< Set input at VDD/2.
106 } nrf_saadc_resistor_t;
107
108
109 /**
110 * @brief Gain factor of the analog-to-digital converter input.
111 */
112 typedef enum
113 {
114 NRF_SAADC_GAIN1_6 = SAADC_CH_CONFIG_GAIN_Gain1_6, ///< Gain factor 1/6.
115 NRF_SAADC_GAIN1_5 = SAADC_CH_CONFIG_GAIN_Gain1_5, ///< Gain factor 1/5.
116 NRF_SAADC_GAIN1_4 = SAADC_CH_CONFIG_GAIN_Gain1_4, ///< Gain factor 1/4.
117 NRF_SAADC_GAIN1_3 = SAADC_CH_CONFIG_GAIN_Gain1_3, ///< Gain factor 1/3.
118 NRF_SAADC_GAIN1_2 = SAADC_CH_CONFIG_GAIN_Gain1_2, ///< Gain factor 1/2.
119 NRF_SAADC_GAIN1 = SAADC_CH_CONFIG_GAIN_Gain1, ///< Gain factor 1.
120 NRF_SAADC_GAIN2 = SAADC_CH_CONFIG_GAIN_Gain2, ///< Gain factor 2.
121 NRF_SAADC_GAIN4 = SAADC_CH_CONFIG_GAIN_Gain4, ///< Gain factor 4.
122 } nrf_saadc_gain_t;
123
124
125 /**
126 * @brief Reference selection for the analog-to-digital converter.
127 */
128 typedef enum
129 {
130 NRF_SAADC_REFERENCE_INTERNAL = SAADC_CH_CONFIG_REFSEL_Internal, ///< Internal reference (0.6 V).
131 NRF_SAADC_REFERENCE_VDD4 = SAADC_CH_CONFIG_REFSEL_VDD1_4 ///< VDD/4 as reference.
132 } nrf_saadc_reference_t;
133
134
135 /**
136 * @brief Analog-to-digital converter acquisition time.
137 */
138 typedef enum
139 {
140 NRF_SAADC_ACQTIME_3US = SAADC_CH_CONFIG_TACQ_3us, ///< 3 us.
141 NRF_SAADC_ACQTIME_5US = SAADC_CH_CONFIG_TACQ_5us, ///< 5 us.
142 NRF_SAADC_ACQTIME_10US = SAADC_CH_CONFIG_TACQ_10us, ///< 10 us.
143 NRF_SAADC_ACQTIME_15US = SAADC_CH_CONFIG_TACQ_15us, ///< 15 us.
144 NRF_SAADC_ACQTIME_20US = SAADC_CH_CONFIG_TACQ_20us, ///< 20 us.
145 NRF_SAADC_ACQTIME_40US = SAADC_CH_CONFIG_TACQ_40us ///< 40 us.
146 } nrf_saadc_acqtime_t;
147
148
149 /**
150 * @brief Analog-to-digital converter channel mode.
151 */
152 typedef enum
153 {
154 NRF_SAADC_MODE_SINGLE_ENDED = SAADC_CH_CONFIG_MODE_SE, ///< Single ended, PSELN will be ignored, negative input to ADC shorted to GND.
155 NRF_SAADC_MODE_DIFFERENTIAL = SAADC_CH_CONFIG_MODE_Diff ///< Differential mode.
156 } nrf_saadc_mode_t;
157
158
159 /**
160 * @brief Analog-to-digital converter channel burst mode.
161 */
162 typedef enum
163 {
164 NRF_SAADC_BURST_DISABLED = SAADC_CH_CONFIG_BURST_Disabled, ///< Burst mode is disabled (normal operation).
165 NRF_SAADC_BURST_ENABLED = SAADC_CH_CONFIG_BURST_Enabled ///< Burst mode is enabled. SAADC takes 2^OVERSAMPLE number of samples as fast as it can, and sends the average to Data RAM.
166 } nrf_saadc_burst_t;
167
168
169 /**
170 * @brief Analog-to-digital converter tasks.
171 */
172 typedef enum /*lint -save -e30 -esym(628,__INTADDR__) */
173 {
174 NRF_SAADC_TASK_START = offsetof(NRF_SAADC_Type, TASKS_START), ///< Start the ADC and prepare the result buffer in RAM.
175 NRF_SAADC_TASK_SAMPLE = offsetof(NRF_SAADC_Type, TASKS_SAMPLE), ///< Take one ADC sample. If scan is enabled, all channels are sampled.
176 NRF_SAADC_TASK_STOP = offsetof(NRF_SAADC_Type, TASKS_STOP), ///< Stop the ADC and terminate any on-going conversion.
177 NRF_SAADC_TASK_CALIBRATEOFFSET = offsetof(NRF_SAADC_Type, TASKS_CALIBRATEOFFSET), ///< Starts offset auto-calibration.
178 } nrf_saadc_task_t;
179
180
181 /**
182 * @brief Analog-to-digital converter events.
183 */
184 typedef enum /*lint -save -e30 -esym(628,__INTADDR__) */
185 {
186 NRF_SAADC_EVENT_STARTED = offsetof(NRF_SAADC_Type, EVENTS_STARTED), ///< The ADC has started.
187 NRF_SAADC_EVENT_END = offsetof(NRF_SAADC_Type, EVENTS_END), ///< The ADC has filled up the result buffer.
188 NRF_SAADC_EVENT_DONE = offsetof(NRF_SAADC_Type, EVENTS_DONE), ///< A conversion task has been completed.
189 NRF_SAADC_EVENT_RESULTDONE = offsetof(NRF_SAADC_Type, EVENTS_RESULTDONE), ///< A result is ready to get transferred to RAM.
190 NRF_SAADC_EVENT_CALIBRATEDONE = offsetof(NRF_SAADC_Type, EVENTS_CALIBRATEDONE), ///< Calibration is complete.
191 NRF_SAADC_EVENT_STOPPED = offsetof(NRF_SAADC_Type, EVENTS_STOPPED), ///< The ADC has stopped.
192 NRF_SAADC_EVENT_CH0_LIMITH = offsetof(NRF_SAADC_Type, EVENTS_CH[0].LIMITH), ///< Last result is equal or above CH[0].LIMIT.HIGH.
193 NRF_SAADC_EVENT_CH0_LIMITL = offsetof(NRF_SAADC_Type, EVENTS_CH[0].LIMITL), ///< Last result is equal or below CH[0].LIMIT.LOW.
194 NRF_SAADC_EVENT_CH1_LIMITH = offsetof(NRF_SAADC_Type, EVENTS_CH[1].LIMITH), ///< Last result is equal or above CH[1].LIMIT.HIGH.
195 NRF_SAADC_EVENT_CH1_LIMITL = offsetof(NRF_SAADC_Type, EVENTS_CH[1].LIMITL), ///< Last result is equal or below CH[1].LIMIT.LOW.
196 NRF_SAADC_EVENT_CH2_LIMITH = offsetof(NRF_SAADC_Type, EVENTS_CH[2].LIMITH), ///< Last result is equal or above CH[2].LIMIT.HIGH.
197 NRF_SAADC_EVENT_CH2_LIMITL = offsetof(NRF_SAADC_Type, EVENTS_CH[2].LIMITL), ///< Last result is equal or below CH[2].LIMIT.LOW.
198 NRF_SAADC_EVENT_CH3_LIMITH = offsetof(NRF_SAADC_Type, EVENTS_CH[3].LIMITH), ///< Last result is equal or above CH[3].LIMIT.HIGH.
199 NRF_SAADC_EVENT_CH3_LIMITL = offsetof(NRF_SAADC_Type, EVENTS_CH[3].LIMITL), ///< Last result is equal or below CH[3].LIMIT.LOW.
200 NRF_SAADC_EVENT_CH4_LIMITH = offsetof(NRF_SAADC_Type, EVENTS_CH[4].LIMITH), ///< Last result is equal or above CH[4].LIMIT.HIGH.
201 NRF_SAADC_EVENT_CH4_LIMITL = offsetof(NRF_SAADC_Type, EVENTS_CH[4].LIMITL), ///< Last result is equal or below CH[4].LIMIT.LOW.
202 NRF_SAADC_EVENT_CH5_LIMITH = offsetof(NRF_SAADC_Type, EVENTS_CH[5].LIMITH), ///< Last result is equal or above CH[5].LIMIT.HIGH.
203 NRF_SAADC_EVENT_CH5_LIMITL = offsetof(NRF_SAADC_Type, EVENTS_CH[5].LIMITL), ///< Last result is equal or below CH[5].LIMIT.LOW.
204 NRF_SAADC_EVENT_CH6_LIMITH = offsetof(NRF_SAADC_Type, EVENTS_CH[6].LIMITH), ///< Last result is equal or above CH[6].LIMIT.HIGH.
205 NRF_SAADC_EVENT_CH6_LIMITL = offsetof(NRF_SAADC_Type, EVENTS_CH[6].LIMITL), ///< Last result is equal or below CH[6].LIMIT.LOW.
206 NRF_SAADC_EVENT_CH7_LIMITH = offsetof(NRF_SAADC_Type, EVENTS_CH[7].LIMITH), ///< Last result is equal or above CH[7].LIMIT.HIGH.
207 NRF_SAADC_EVENT_CH7_LIMITL = offsetof(NRF_SAADC_Type, EVENTS_CH[7].LIMITL) ///< Last result is equal or below CH[7].LIMIT.LOW.
208 } nrf_saadc_event_t;
209
210
211 /**
212 * @brief Analog-to-digital converter interrupt masks.
213 */
214 typedef enum
215 {
216 NRF_SAADC_INT_STARTED = SAADC_INTENSET_STARTED_Msk, ///< Interrupt on EVENTS_STARTED event.
217 NRF_SAADC_INT_END = SAADC_INTENSET_END_Msk, ///< Interrupt on EVENTS_END event.
218 NRF_SAADC_INT_DONE = SAADC_INTENSET_DONE_Msk, ///< Interrupt on EVENTS_DONE event.
219 NRF_SAADC_INT_RESULTDONE = SAADC_INTENSET_RESULTDONE_Msk, ///< Interrupt on EVENTS_RESULTDONE event.
220 NRF_SAADC_INT_CALIBRATEDONE = SAADC_INTENSET_CALIBRATEDONE_Msk, ///< Interrupt on EVENTS_CALIBRATEDONE event.
221 NRF_SAADC_INT_STOPPED = SAADC_INTENSET_STOPPED_Msk, ///< Interrupt on EVENTS_STOPPED event.
222 NRF_SAADC_INT_CH0LIMITH = SAADC_INTENSET_CH0LIMITH_Msk, ///< Interrupt on EVENTS_CH[0].LIMITH event.
223 NRF_SAADC_INT_CH0LIMITL = SAADC_INTENSET_CH0LIMITL_Msk, ///< Interrupt on EVENTS_CH[0].LIMITL event.
224 NRF_SAADC_INT_CH1LIMITH = SAADC_INTENSET_CH1LIMITH_Msk, ///< Interrupt on EVENTS_CH[1].LIMITH event.
225 NRF_SAADC_INT_CH1LIMITL = SAADC_INTENSET_CH1LIMITL_Msk, ///< Interrupt on EVENTS_CH[1].LIMITL event.
226 NRF_SAADC_INT_CH2LIMITH = SAADC_INTENSET_CH2LIMITH_Msk, ///< Interrupt on EVENTS_CH[2].LIMITH event.
227 NRF_SAADC_INT_CH2LIMITL = SAADC_INTENSET_CH2LIMITL_Msk, ///< Interrupt on EVENTS_CH[2].LIMITL event.
228 NRF_SAADC_INT_CH3LIMITH = SAADC_INTENSET_CH3LIMITH_Msk, ///< Interrupt on EVENTS_CH[3].LIMITH event.
229 NRF_SAADC_INT_CH3LIMITL = SAADC_INTENSET_CH3LIMITL_Msk, ///< Interrupt on EVENTS_CH[3].LIMITL event.
230 NRF_SAADC_INT_CH4LIMITH = SAADC_INTENSET_CH4LIMITH_Msk, ///< Interrupt on EVENTS_CH[4].LIMITH event.
231 NRF_SAADC_INT_CH4LIMITL = SAADC_INTENSET_CH4LIMITL_Msk, ///< Interrupt on EVENTS_CH[4].LIMITL event.
232 NRF_SAADC_INT_CH5LIMITH = SAADC_INTENSET_CH5LIMITH_Msk, ///< Interrupt on EVENTS_CH[5].LIMITH event.
233 NRF_SAADC_INT_CH5LIMITL = SAADC_INTENSET_CH5LIMITL_Msk, ///< Interrupt on EVENTS_CH[5].LIMITL event.
234 NRF_SAADC_INT_CH6LIMITH = SAADC_INTENSET_CH6LIMITH_Msk, ///< Interrupt on EVENTS_CH[6].LIMITH event.
235 NRF_SAADC_INT_CH6LIMITL = SAADC_INTENSET_CH6LIMITL_Msk, ///< Interrupt on EVENTS_CH[6].LIMITL event.
236 NRF_SAADC_INT_CH7LIMITH = SAADC_INTENSET_CH7LIMITH_Msk, ///< Interrupt on EVENTS_CH[7].LIMITH event.
237 NRF_SAADC_INT_CH7LIMITL = SAADC_INTENSET_CH7LIMITL_Msk, ///< Interrupt on EVENTS_CH[7].LIMITL event.
238 NRF_SAADC_INT_ALL = 0x7FFFFFFFUL ///< Mask of all interrupts.
239 } nrf_saadc_int_mask_t;
240
241
242 /**
243 * @brief Analog-to-digital converter value limit type.
244 */
245 typedef enum
246 {
247 NRF_SAADC_LIMIT_LOW = 0,
248 NRF_SAADC_LIMIT_HIGH = 1
249 } nrf_saadc_limit_t;
250
251
252 typedef int16_t nrf_saadc_value_t; ///< Type of a single ADC conversion result.
253
254
255 /**
256 * @brief Analog-to-digital converter configuration structure.
257 */
258 typedef struct
259 {
260 nrf_saadc_resolution_t resolution;
261 nrf_saadc_oversample_t oversample;
262 nrf_saadc_value_t * buffer;
263 uint32_t buffer_size;
264 } nrf_saadc_config_t;
265
266
267 /**
268 * @brief Analog-to-digital converter channel configuration structure.
269 */
270 typedef struct
271 {
272 nrf_saadc_resistor_t resistor_p;
273 nrf_saadc_resistor_t resistor_n;
274 nrf_saadc_gain_t gain;
275 nrf_saadc_reference_t reference;
276 nrf_saadc_acqtime_t acq_time;
277 nrf_saadc_mode_t mode;
278 nrf_saadc_burst_t burst;
279 nrf_saadc_input_t pin_p;
280 nrf_saadc_input_t pin_n;
281 } nrf_saadc_channel_config_t;
282
283 /**
284 * @brief Function for triggering a specific SAADC task.
285 *
286 * @param[in] saadc_task SAADC task.
287 */
288 __STATIC_INLINE void nrf_saadc_task_trigger(nrf_saadc_task_t saadc_task);
289
290 /**
291 * @brief Function for getting the address of a specific SAADC task register.
292 *
293 * @param[in] saadc_task SAADC task.
294 *
295 * @return Address of the specified SAADC task.
296 */
297 __STATIC_INLINE uint32_t nrf_saadc_task_address_get(nrf_saadc_task_t saadc_task);
298
299 /**
300 * @brief Function for getting the state of a specific SAADC event.
301 *
302 * @param[in] saadc_event SAADC event.
303 *
304 * @return State of the specified SAADC event.
305 */
306 __STATIC_INLINE bool nrf_saadc_event_check(nrf_saadc_event_t saadc_event);
307
308 /**
309 * @brief Function for clearing the specific SAADC event.
310 *
311 * @param[in] saadc_event SAADC event.
312 */
313 __STATIC_INLINE void nrf_saadc_event_clear(nrf_saadc_event_t saadc_event);
314
315 /**
316 * @brief Function for getting the address of a specific SAADC event register.
317 *
318 * @param[in] saadc_event SAADC event.
319 *
320 * @return Address of the specified SAADC event.
321 */
322 __STATIC_INLINE uint32_t nrf_saadc_event_address_get(nrf_saadc_event_t saadc_event);
323
324 #if defined(DPPI_PRESENT) || defined(__NRFX_DOXYGEN__)
325 /**
326 * @brief Function for setting the subscribe configuration for a given
327 * SAADC task.
328 *
329 * @param[in] task Task for which to set the configuration.
330 * @param[in] channel Channel through which to subscribe events.
331 */
332 __STATIC_INLINE void nrf_saadc_subscribe_set(nrf_saadc_task_t task,
333 uint8_t channel);
334
335 /**
336 * @brief Function for clearing the subscribe configuration for a given
337 * SAADC task.
338 *
339 * @param[in] task Task for which to clear the configuration.
340 */
341 __STATIC_INLINE void nrf_saadc_subscribe_clear(nrf_saadc_task_t task);
342
343 /**
344 * @brief Function for setting the publish configuration for a given
345 * SAADC event.
346 *
347 * @param[in] event Event for which to set the configuration.
348 * @param[in] channel Channel through which to publish the event.
349 */
350 __STATIC_INLINE void nrf_saadc_publish_set(nrf_saadc_event_t event,
351 uint8_t channel);
352
353 /**
354 * @brief Function for clearing the publish configuration for a given
355 * SAADC event.
356 *
357 * @param[in] event Event for which to clear the configuration.
358 */
359 __STATIC_INLINE void nrf_saadc_publish_clear(nrf_saadc_event_t event);
360 #endif // defined(DPPI_PRESENT) || defined(__NRFX_DOXYGEN__)
361
362 /**
363 * @brief Function for getting the address of a specific SAADC limit event register.
364 *
365 * @param[in] channel Channel number.
366 * @param[in] limit_type Low limit or high limit.
367 *
368 * @return Address of the specified SAADC limit event.
369 */
370 __STATIC_INLINE volatile uint32_t * nrf_saadc_event_limit_address_get(uint8_t channel, nrf_saadc_limit_t limit_type);
371
372 /**
373 * @brief Function for getting the SAADC channel monitoring limit events.
374 *
375 * @param[in] channel Channel number.
376 * @param[in] limit_type Low limit or high limit.
377 */
378 __STATIC_INLINE nrf_saadc_event_t nrf_saadc_event_limit_get(uint8_t channel, nrf_saadc_limit_t limit_type);
379
380 /**
381 * @brief Function for configuring the input pins for a specific SAADC channel.
382 *
383 * @param[in] channel Channel number.
384 * @param[in] pselp Positive input.
385 * @param[in] pseln Negative input. Set to NRF_SAADC_INPUT_DISABLED in single ended mode.
386 */
387 __STATIC_INLINE void nrf_saadc_channel_input_set(uint8_t channel,
388 nrf_saadc_input_t pselp,
389 nrf_saadc_input_t pseln);
390
391 /**
392 * @brief Function for configuring the positive input pin for a specific SAADC channel.
393 *
394 * @param[in] channel Channel number.
395 * @param[in] pselp Positive input.
396 */
397 __STATIC_INLINE void nrf_saadc_channel_pos_input_set(uint8_t channel,
398 nrf_saadc_input_t pselp);
399
400 /**
401 * @brief Function for setting the SAADC channel monitoring limits.
402 *
403 * @param[in] channel Channel number.
404 * @param[in] low Low limit.
405 * @param[in] high High limit.
406 */
407 __STATIC_INLINE void nrf_saadc_channel_limits_set(uint8_t channel, int16_t low, int16_t high);
408
409 /**
410 * @brief Function for enabling specified SAADC interrupts.
411 *
412 * @param[in] saadc_int_mask Interrupt(s) to enable.
413 */
414 __STATIC_INLINE void nrf_saadc_int_enable(uint32_t saadc_int_mask);
415
416 /**
417 * @brief Function for retrieving the state of specified SAADC interrupts.
418 *
419 * @param[in] saadc_int_mask Interrupt(s) to check.
420 *
421 * @retval true If all specified interrupts are enabled.
422 * @retval false If at least one of the given interrupts is not enabled.
423 */
424 __STATIC_INLINE bool nrf_saadc_int_enable_check(uint32_t saadc_int_mask);
425
426 /**
427 * @brief Function for disabling specified interrupts.
428 *
429 * @param saadc_int_mask Interrupt(s) to disable.
430 */
431 __STATIC_INLINE void nrf_saadc_int_disable(uint32_t saadc_int_mask);
432
433 /**
434 * @brief Function for generating masks for SAADC channel limit interrupts.
435 *
436 * @param[in] channel SAADC channel number.
437 * @param[in] limit_type Limit type.
438 *
439 * @returns Interrupt mask.
440 */
441 __STATIC_INLINE uint32_t nrf_saadc_limit_int_get(uint8_t channel, nrf_saadc_limit_t limit_type);
442
443 /**
444 * @brief Function for checking whether the SAADC is busy.
445 *
446 * This function checks whether the analog-to-digital converter is busy with a conversion.
447 *
448 * @retval true If the SAADC is busy.
449 * @retval false If the SAADC is not busy.
450 */
451 __STATIC_INLINE bool nrf_saadc_busy_check(void);
452
453 /**
454 * @brief Function for enabling the SAADC.
455 *
456 * The analog-to-digital converter must be enabled before use.
457 */
458 __STATIC_INLINE void nrf_saadc_enable(void);
459
460 /**
461 * @brief Function for disabling the SAADC.
462 */
463 __STATIC_INLINE void nrf_saadc_disable(void);
464
465 /**
466 * @brief Function for checking if the SAADC is enabled.
467 *
468 * @retval true If the SAADC is enabled.
469 * @retval false If the SAADC is not enabled.
470 */
471 __STATIC_INLINE bool nrf_saadc_enable_check(void);
472
473 /**
474 * @brief Function for initializing the SAADC result buffer.
475 *
476 * @param[in] p_buffer Pointer to the result buffer.
477 * @param[in] size Size of the buffer (in 16-bit samples).
478 */
479 __STATIC_INLINE void nrf_saadc_buffer_init(nrf_saadc_value_t * p_buffer,
480 uint32_t size);
481
482 /**
483 * @brief Function for setting the SAADC result buffer pointer.
484 *
485 * @param[in] p_buffer Pointer to the result buffer.
486 */
487 __STATIC_INLINE void nrf_saadc_buffer_pointer_set(nrf_saadc_value_t * p_buffer);
488
489 /**
490 * @brief Function for getting the SAADC result buffer pointer.
491 *
492 * @return Pointer to the result buffer.
493 */
494 __STATIC_INLINE nrf_saadc_value_t * nrf_saadc_buffer_pointer_get(void);
495
496 /**
497 * @brief Function for getting the number of samples written to the result
498 * buffer since the previous START task.
499 *
500 * @returns Number of 16-bit samples written to the buffer.
501 */
502 __STATIC_INLINE uint16_t nrf_saadc_amount_get(void);
503
504 /**
505 * @brief Function for setting the SAADC sample resolution.
506 *
507 * @param[in] resolution Bit resolution.
508 */
509 __STATIC_INLINE void nrf_saadc_resolution_set(nrf_saadc_resolution_t resolution);
510
511 /**
512 * @brief Function for configuring the oversampling feature.
513 *
514 * @param[in] oversample Oversampling mode.
515 */
516 __STATIC_INLINE void nrf_saadc_oversample_set(nrf_saadc_oversample_t oversample);
517
518 /**
519 * @brief Function for getting the oversampling feature configuration.
520 *
521 * @return Oversampling configuration.
522 */
523 __STATIC_INLINE nrf_saadc_oversample_t nrf_saadc_oversample_get(void);
524
525 /**
526 * @brief Function for initializing the SAADC channel.
527 *
528 * @param[in] channel Channel number.
529 * @param[in] config Pointer to the channel configuration structure.
530 */
531 __STATIC_INLINE void nrf_saadc_channel_init(uint8_t channel,
532 nrf_saadc_channel_config_t const * const config);
533
534 /**
535 * @brief Function for configuring the burst mode for the specified channel.
536 *
537 * @param[in] channel Channel number.
538 * @param[in] burst Burst mode setting.
539 */
540 __STATIC_INLINE void nrf_saadc_burst_set(uint8_t channel,
541 nrf_saadc_burst_t burst);
542
543 #ifndef SUPPRESS_INLINE_IMPLEMENTATION
544
nrf_saadc_task_trigger(nrf_saadc_task_t saadc_task)545 __STATIC_INLINE void nrf_saadc_task_trigger(nrf_saadc_task_t saadc_task)
546 {
547 *((volatile uint32_t *)((uint8_t *)NRF_SAADC + (uint32_t)saadc_task)) = 0x1UL;
548 }
549
nrf_saadc_task_address_get(nrf_saadc_task_t saadc_task)550 __STATIC_INLINE uint32_t nrf_saadc_task_address_get(nrf_saadc_task_t saadc_task)
551 {
552 return (uint32_t)((uint8_t *)NRF_SAADC + (uint32_t)saadc_task);
553 }
554
nrf_saadc_event_check(nrf_saadc_event_t saadc_event)555 __STATIC_INLINE bool nrf_saadc_event_check(nrf_saadc_event_t saadc_event)
556 {
557 return (bool)*(volatile uint32_t *)((uint8_t *)NRF_SAADC + (uint32_t)saadc_event);
558 }
559
nrf_saadc_event_clear(nrf_saadc_event_t saadc_event)560 __STATIC_INLINE void nrf_saadc_event_clear(nrf_saadc_event_t saadc_event)
561 {
562 *((volatile uint32_t *)((uint8_t *)NRF_SAADC + (uint32_t)saadc_event)) = 0x0UL;
563 #if __CORTEX_M == 0x04
564 volatile uint32_t dummy = *((volatile uint32_t *)((uint8_t *)NRF_SAADC + (uint32_t)saadc_event));
565 (void)dummy;
566 #endif
567 }
568
nrf_saadc_event_address_get(nrf_saadc_event_t saadc_event)569 __STATIC_INLINE uint32_t nrf_saadc_event_address_get(nrf_saadc_event_t saadc_event)
570 {
571 return (uint32_t )((uint8_t *)NRF_SAADC + (uint32_t)saadc_event);
572 }
573
574 #if defined(DPPI_PRESENT)
nrf_saadc_subscribe_set(nrf_saadc_task_t task,uint8_t channel)575 __STATIC_INLINE void nrf_saadc_subscribe_set(nrf_saadc_task_t task,
576 uint8_t channel)
577 {
578 *((volatile uint32_t *) ((uint8_t *) NRF_SAADC + (uint32_t) task + 0x80uL)) =
579 ((uint32_t)channel | SAADC_SUBSCRIBE_START_EN_Msk);
580 }
581
nrf_saadc_subscribe_clear(nrf_saadc_task_t task)582 __STATIC_INLINE void nrf_saadc_subscribe_clear(nrf_saadc_task_t task)
583 {
584 *((volatile uint32_t *) ((uint8_t *) NRF_SAADC + (uint32_t) task + 0x80uL)) = 0;
585 }
586
nrf_saadc_publish_set(nrf_saadc_event_t event,uint8_t channel)587 __STATIC_INLINE void nrf_saadc_publish_set(nrf_saadc_event_t event,
588 uint8_t channel)
589 {
590 *((volatile uint32_t *) ((uint8_t *) NRF_SAADC + (uint32_t) event + 0x80uL)) =
591 ((uint32_t)channel | SAADC_PUBLISH_STARTED_EN_Msk);
592 }
593
nrf_saadc_publish_clear(nrf_saadc_event_t event)594 __STATIC_INLINE void nrf_saadc_publish_clear(nrf_saadc_event_t event)
595 {
596 *((volatile uint32_t *) ((uint8_t *) NRF_SAADC + (uint32_t) event + 0x80uL)) = 0;
597 }
598 #endif // defined(DPPI_PRESENT)
599
nrf_saadc_event_limit_address_get(uint8_t channel,nrf_saadc_limit_t limit_type)600 __STATIC_INLINE volatile uint32_t * nrf_saadc_event_limit_address_get(uint8_t channel, nrf_saadc_limit_t limit_type)
601 {
602 NRFX_ASSERT(channel < NRF_SAADC_CHANNEL_COUNT);
603 if (limit_type == NRF_SAADC_LIMIT_HIGH)
604 {
605 return &NRF_SAADC->EVENTS_CH[channel].LIMITH;
606 }
607 else
608 {
609 return &NRF_SAADC->EVENTS_CH[channel].LIMITL;
610 }
611 }
612
nrf_saadc_event_limit_get(uint8_t channel,nrf_saadc_limit_t limit_type)613 __STATIC_INLINE nrf_saadc_event_t nrf_saadc_event_limit_get(uint8_t channel, nrf_saadc_limit_t limit_type)
614 {
615 if (limit_type == NRF_SAADC_LIMIT_HIGH)
616 {
617 return (nrf_saadc_event_t)( (uint32_t) NRF_SAADC_EVENT_CH0_LIMITH +
618 (uint32_t) (NRF_SAADC_EVENT_CH1_LIMITH - NRF_SAADC_EVENT_CH0_LIMITH)
619 * (uint32_t) channel );
620 }
621 else
622 {
623 return (nrf_saadc_event_t)( (uint32_t) NRF_SAADC_EVENT_CH0_LIMITL +
624 (uint32_t) (NRF_SAADC_EVENT_CH1_LIMITL - NRF_SAADC_EVENT_CH0_LIMITL)
625 * (uint32_t) channel );
626 }
627 }
628
nrf_saadc_channel_input_set(uint8_t channel,nrf_saadc_input_t pselp,nrf_saadc_input_t pseln)629 __STATIC_INLINE void nrf_saadc_channel_input_set(uint8_t channel,
630 nrf_saadc_input_t pselp,
631 nrf_saadc_input_t pseln)
632 {
633 NRF_SAADC->CH[channel].PSELN = pseln;
634 NRF_SAADC->CH[channel].PSELP = pselp;
635 }
636
nrf_saadc_channel_pos_input_set(uint8_t channel,nrf_saadc_input_t pselp)637 __STATIC_INLINE void nrf_saadc_channel_pos_input_set(uint8_t channel,
638 nrf_saadc_input_t pselp)
639 {
640 NRF_SAADC->CH[channel].PSELP = pselp;
641 }
642
nrf_saadc_channel_limits_set(uint8_t channel,int16_t low,int16_t high)643 __STATIC_INLINE void nrf_saadc_channel_limits_set(uint8_t channel, int16_t low, int16_t high)
644 {
645 NRF_SAADC->CH[channel].LIMIT = (
646 (((uint32_t) low << SAADC_CH_LIMIT_LOW_Pos) & SAADC_CH_LIMIT_LOW_Msk)
647 | (((uint32_t) high << SAADC_CH_LIMIT_HIGH_Pos) & SAADC_CH_LIMIT_HIGH_Msk));
648 }
649
nrf_saadc_int_enable(uint32_t saadc_int_mask)650 __STATIC_INLINE void nrf_saadc_int_enable(uint32_t saadc_int_mask)
651 {
652 NRF_SAADC->INTENSET = saadc_int_mask;
653 }
654
nrf_saadc_int_enable_check(uint32_t saadc_int_mask)655 __STATIC_INLINE bool nrf_saadc_int_enable_check(uint32_t saadc_int_mask)
656 {
657 return (bool)(NRF_SAADC->INTENSET & saadc_int_mask);
658 }
659
nrf_saadc_int_disable(uint32_t saadc_int_mask)660 __STATIC_INLINE void nrf_saadc_int_disable(uint32_t saadc_int_mask)
661 {
662 NRF_SAADC->INTENCLR = saadc_int_mask;
663 }
664
nrf_saadc_limit_int_get(uint8_t channel,nrf_saadc_limit_t limit_type)665 __STATIC_INLINE uint32_t nrf_saadc_limit_int_get(uint8_t channel, nrf_saadc_limit_t limit_type)
666 {
667 NRFX_ASSERT(channel < NRF_SAADC_CHANNEL_COUNT);
668 uint32_t mask = (limit_type == NRF_SAADC_LIMIT_LOW) ? NRF_SAADC_INT_CH0LIMITL : NRF_SAADC_INT_CH0LIMITH;
669 return mask << (channel * 2);
670 }
671
nrf_saadc_busy_check(void)672 __STATIC_INLINE bool nrf_saadc_busy_check(void)
673 {
674 //return ((NRF_SAADC->STATUS & SAADC_STATUS_STATUS_Msk) == SAADC_STATUS_STATUS_Msk);
675 //simplified for performance
676 return NRF_SAADC->STATUS;
677 }
678
nrf_saadc_enable(void)679 __STATIC_INLINE void nrf_saadc_enable(void)
680 {
681 NRF_SAADC->ENABLE = (SAADC_ENABLE_ENABLE_Enabled << SAADC_ENABLE_ENABLE_Pos);
682 }
683
nrf_saadc_disable(void)684 __STATIC_INLINE void nrf_saadc_disable(void)
685 {
686 NRF_SAADC->ENABLE = (SAADC_ENABLE_ENABLE_Disabled << SAADC_ENABLE_ENABLE_Pos);
687 }
688
nrf_saadc_enable_check(void)689 __STATIC_INLINE bool nrf_saadc_enable_check(void)
690 {
691 //simplified for performance
692 return NRF_SAADC->ENABLE;
693 }
694
nrf_saadc_buffer_init(nrf_saadc_value_t * p_buffer,uint32_t size)695 __STATIC_INLINE void nrf_saadc_buffer_init(nrf_saadc_value_t * p_buffer,
696 uint32_t size)
697 {
698 NRF_SAADC->RESULT.PTR = (uint32_t)p_buffer;
699 NRF_SAADC->RESULT.MAXCNT = size;
700 }
701
nrf_saadc_buffer_pointer_set(nrf_saadc_value_t * p_buffer)702 __STATIC_INLINE void nrf_saadc_buffer_pointer_set(nrf_saadc_value_t * p_buffer)
703 {
704 NRF_SAADC->RESULT.PTR = (uint32_t)p_buffer;
705 }
706
nrf_saadc_buffer_pointer_get(void)707 __STATIC_INLINE nrf_saadc_value_t * nrf_saadc_buffer_pointer_get(void)
708 {
709 return (nrf_saadc_value_t *)NRF_SAADC->RESULT.PTR;
710 }
711
nrf_saadc_amount_get(void)712 __STATIC_INLINE uint16_t nrf_saadc_amount_get(void)
713 {
714 return NRF_SAADC->RESULT.AMOUNT;
715 }
716
nrf_saadc_resolution_set(nrf_saadc_resolution_t resolution)717 __STATIC_INLINE void nrf_saadc_resolution_set(nrf_saadc_resolution_t resolution)
718 {
719 NRF_SAADC->RESOLUTION = resolution;
720 }
721
nrf_saadc_oversample_set(nrf_saadc_oversample_t oversample)722 __STATIC_INLINE void nrf_saadc_oversample_set(nrf_saadc_oversample_t oversample)
723 {
724 NRF_SAADC->OVERSAMPLE = oversample;
725 }
726
nrf_saadc_oversample_get(void)727 __STATIC_INLINE nrf_saadc_oversample_t nrf_saadc_oversample_get(void)
728 {
729 return (nrf_saadc_oversample_t)NRF_SAADC->OVERSAMPLE;
730 }
731
nrf_saadc_channel_init(uint8_t channel,nrf_saadc_channel_config_t const * const config)732 __STATIC_INLINE void nrf_saadc_channel_init(uint8_t channel,
733 nrf_saadc_channel_config_t const * const config)
734 {
735 NRF_SAADC->CH[channel].CONFIG =
736 ((config->resistor_p << SAADC_CH_CONFIG_RESP_Pos) & SAADC_CH_CONFIG_RESP_Msk)
737 | ((config->resistor_n << SAADC_CH_CONFIG_RESN_Pos) & SAADC_CH_CONFIG_RESN_Msk)
738 | ((config->gain << SAADC_CH_CONFIG_GAIN_Pos) & SAADC_CH_CONFIG_GAIN_Msk)
739 | ((config->reference << SAADC_CH_CONFIG_REFSEL_Pos) & SAADC_CH_CONFIG_REFSEL_Msk)
740 | ((config->acq_time << SAADC_CH_CONFIG_TACQ_Pos) & SAADC_CH_CONFIG_TACQ_Msk)
741 | ((config->mode << SAADC_CH_CONFIG_MODE_Pos) & SAADC_CH_CONFIG_MODE_Msk)
742 | ((config->burst << SAADC_CH_CONFIG_BURST_Pos) & SAADC_CH_CONFIG_BURST_Msk);
743 nrf_saadc_channel_input_set(channel, config->pin_p, config->pin_n);
744 }
745
nrf_saadc_burst_set(uint8_t channel,nrf_saadc_burst_t burst)746 __STATIC_INLINE void nrf_saadc_burst_set(uint8_t channel,
747 nrf_saadc_burst_t burst)
748 {
749 NRF_SAADC->CH[channel].CONFIG =
750 (NRF_SAADC->CH[channel].CONFIG & ~SAADC_CH_CONFIG_BURST_Msk) |
751 (burst << SAADC_CH_CONFIG_BURST_Pos);
752 }
753
754 #endif // SUPPRESS_INLINE_IMPLEMENTATION
755
756 /** @} */
757
758 #ifdef __cplusplus
759 }
760 #endif
761
762 #endif // NRF_SAADC_H_
763