1 //***************************************************************************** 2 // 3 // am_hal_adc.h 4 //! @file 5 //! 6 //! @brief Functions for interfacing with the Analog to Digital Converter 7 //! 8 //! @addtogroup adc2 Analog-to-Digital Converter (ADC) 9 //! @ingroup apollo2hal 10 //! @{ 11 // 12 //***************************************************************************** 13 14 //***************************************************************************** 15 // 16 // Copyright (c) 2017, Ambiq Micro 17 // All rights reserved. 18 // 19 // Redistribution and use in source and binary forms, with or without 20 // modification, are permitted provided that the following conditions are met: 21 // 22 // 1. Redistributions of source code must retain the above copyright notice, 23 // this list of conditions and the following disclaimer. 24 // 25 // 2. Redistributions in binary form must reproduce the above copyright 26 // notice, this list of conditions and the following disclaimer in the 27 // documentation and/or other materials provided with the distribution. 28 // 29 // 3. Neither the name of the copyright holder nor the names of its 30 // contributors may be used to endorse or promote products derived from this 31 // software without specific prior written permission. 32 // 33 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 34 // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 35 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 36 // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE 37 // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 38 // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 39 // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 40 // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 41 // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 42 // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 43 // POSSIBILITY OF SUCH DAMAGE. 44 // 45 // This is part of revision 1.2.11 of the AmbiqSuite Development Package. 46 // 47 //***************************************************************************** 48 #ifndef AM_HAL_ADC_H 49 #define AM_HAL_ADC_H 50 51 //***************************************************************************** 52 // 53 //! @name Clock Selection 54 //! @brief These macros may be used to set the ADC module's clock source. 55 //! @{ 56 // 57 //***************************************************************************** 58 #define AM_HAL_ADC_CLOCK_OFF AM_REG_ADC_CFG_CLKSEL_OFF 59 #define AM_HAL_ADC_CLOCK_HFRC AM_REG_ADC_CFG_CLKSEL_HFRC 60 #define AM_HAL_ADC_CLOCK_DIV2 AM_REG_ADC_CFG_CLKSEL_HFRC_DIV2 61 //! @} 62 63 //***************************************************************************** 64 // 65 //! @name Trigger Settings 66 //! @brief ADC trigger setting macros. 67 //! 68 //! These macros alter the ADC's trigger source and trigger polarity. Note that 69 //! the external trigger setting needs to be ORed with a POS or NEG option to 70 //! define the desired trigger polarity. 71 //! @{ 72 // 73 //***************************************************************************** 74 #define AM_HAL_ADC_TRIGGER_SOFT AM_REG_ADC_CFG_TRIGSEL_SWT 75 #define AM_HAL_ADC_TRIGGER_VCOMP AM_REG_ADC_CFG_TRIGSEL_VCOMP 76 #define AM_HAL_ADC_TRIGGER_EXT0 AM_REG_ADC_CFG_TRIGSEL_EXT0 77 #define AM_HAL_ADC_TRIGGER_EXT1 AM_REG_ADC_CFG_TRIGSEL_EXT1 78 #define AM_HAL_ADC_TRIGGER_EXT2 AM_REG_ADC_CFG_TRIGSEL_EXT2 79 #define AM_HAL_ADC_TRIGGER_EXT3 AM_REG_ADC_CFG_TRIGSEL_EXT3 80 #define AM_HAL_ADC_TRIGGER_FALL AM_REG_ADC_CFG_TRIGPOL_FALLING_EDGE 81 #define AM_HAL_ADC_TRIGGER_RISE AM_REG_ADC_CFG_TRIGPOL_RISING_EDGE 82 //! @} 83 84 //***************************************************************************** 85 // 86 //! @name Reference Settings 87 //! @brief ADC reference voltage setting macros. 88 //! 89 //! These macros control the ADC reference voltage source. 90 //! @{ 91 // 92 //***************************************************************************** 93 #define AM_HAL_ADC_REF_EXT_2P0 AM_REG_ADC_CFG_REFSEL_EXT2P0 94 #define AM_HAL_ADC_REF_EXT_1P5 AM_REG_ADC_CFG_REFSEL_EXT1P5 95 #define AM_HAL_ADC_REF_INT_2P0 AM_REG_ADC_CFG_REFSEL_INT2P0 96 #define AM_HAL_ADC_REF_INT_1P5 AM_REG_ADC_CFG_REFSEL_INT1P5 97 //! @} 98 99 //***************************************************************************** 100 // 101 //! @name Clock Mode 102 //! @brief ADC clock mode settings 103 //! 104 //! These macros determine whether the ADC shuts down its clock between 105 //! samples. Shutting down the clock will reduce power consumption, but 106 //! increase latency. This setting is only valid for LPMODE 0. For other modes, 107 //! it will be ignored. 108 //! 109 //! @{ 110 // 111 //***************************************************************************** 112 #define AM_HAL_ADC_CK_LOW_POWER AM_REG_ADC_CFG_CKMODE_LPCKMODE 113 #define AM_HAL_ADC_CK_LOW_LATENCY AM_REG_ADC_CFG_CKMODE_LLCKMODE 114 //! @} 115 116 //***************************************************************************** 117 // 118 //! @name Low Power Mode 119 //! @brief ADC power conservation settings. 120 //! 121 //! These macros select the power state to enter between active scans. Each low 122 //! power mode has its own set of timing constraints. Please see the datasheet 123 //! for additional timing information on each power mode. 124 //! @{ 125 // 126 //***************************************************************************** 127 #define AM_HAL_ADC_LPMODE_0 AM_REG_ADC_CFG_LPMODE_MODE0 128 #define AM_HAL_ADC_LPMODE_1 AM_REG_ADC_CFG_LPMODE_MODE1 129 //! @} 130 131 //***************************************************************************** 132 // 133 //! @name Repeat Mode 134 //! @brief Enable repeating scan mode. 135 //! 136 //! Use this macro to enable repeating scans using timer 3. 137 //! 138 //! @{ 139 // 140 //***************************************************************************** 141 #define AM_HAL_ADC_REPEAT AM_REG_ADC_CFG_RPTEN(1) 142 #define AM_HAL_ADC_NO_REPEAT AM_REG_ADC_CFG_RPTEN(0) 143 //! @} 144 145 //***************************************************************************** 146 // 147 //! @name Slot configuration 148 //! @brief Slot configuration macros 149 //! 150 //! These macros may be used to configure an individual ADC slot. 151 //! @{ 152 // 153 //***************************************************************************** 154 155 // Set number of samples to average. 156 #define AM_HAL_ADC_SLOT_AVG_1 AM_REG_ADC_SL0CFG_ADSEL0(0) 157 #define AM_HAL_ADC_SLOT_AVG_2 AM_REG_ADC_SL0CFG_ADSEL0(1) 158 #define AM_HAL_ADC_SLOT_AVG_4 AM_REG_ADC_SL0CFG_ADSEL0(2) 159 #define AM_HAL_ADC_SLOT_AVG_8 AM_REG_ADC_SL0CFG_ADSEL0(3) 160 #define AM_HAL_ADC_SLOT_AVG_16 AM_REG_ADC_SL0CFG_ADSEL0(4) 161 #define AM_HAL_ADC_SLOT_AVG_32 AM_REG_ADC_SL0CFG_ADSEL0(5) 162 #define AM_HAL_ADC_SLOT_AVG_64 AM_REG_ADC_SL0CFG_ADSEL0(6) 163 #define AM_HAL_ADC_SLOT_AVG_128 AM_REG_ADC_SL0CFG_ADSEL0(7) 164 165 // Set slot precision mode. 166 #define AM_HAL_ADC_SLOT_14BIT AM_REG_ADC_SL0CFG_PRMODE0_P14B 167 #define AM_HAL_ADC_SLOT_12BIT AM_REG_ADC_SL0CFG_PRMODE0_P14B 168 #define AM_HAL_ADC_SLOT_10BIT AM_REG_ADC_SL0CFG_PRMODE0_P14B 169 #define AM_HAL_ADC_SLOT_8BIT AM_REG_ADC_SL0CFG_PRMODE0_P14B 170 171 // Select a channel by number. 172 #define AM_HAL_ADC_SLOT_CHANNEL(n) AM_REG_ADC_SL0CFG_CHSEL0(n) 173 174 // Single-ended channels 175 #define AM_HAL_ADC_SLOT_CHSEL_SE0 AM_REG_ADC_SL0CFG_CHSEL0_SE0 176 #define AM_HAL_ADC_SLOT_CHSEL_SE1 AM_REG_ADC_SL0CFG_CHSEL0_SE1 177 #define AM_HAL_ADC_SLOT_CHSEL_SE2 AM_REG_ADC_SL0CFG_CHSEL0_SE2 178 #define AM_HAL_ADC_SLOT_CHSEL_SE3 AM_REG_ADC_SL0CFG_CHSEL0_SE3 179 #define AM_HAL_ADC_SLOT_CHSEL_SE4 AM_REG_ADC_SL0CFG_CHSEL0_SE4 180 #define AM_HAL_ADC_SLOT_CHSEL_SE5 AM_REG_ADC_SL0CFG_CHSEL0_SE5 181 #define AM_HAL_ADC_SLOT_CHSEL_SE6 AM_REG_ADC_SL0CFG_CHSEL0_SE6 182 #define AM_HAL_ADC_SLOT_CHSEL_SE7 AM_REG_ADC_SL0CFG_CHSEL0_SE7 183 #define AM_HAL_ADC_SLOT_CHSEL_SE8 AM_REG_ADC_SL0CFG_CHSEL0_SE8 184 #define AM_HAL_ADC_SLOT_CHSEL_SE9 AM_REG_ADC_SL0CFG_CHSEL0_SE9 185 186 // Differential channels. 187 #define AM_HAL_ADC_SLOT_CHSEL_DF0 AM_REG_ADC_SL0CFG_CHSEL0_DF0 188 #define AM_HAL_ADC_SLOT_CHSEL_DF1 AM_REG_ADC_SL0CFG_CHSEL0_DF1 189 190 // Miscellaneous other signals. 191 #define AM_HAL_ADC_SLOT_CHSEL_TEMP AM_REG_ADC_SL0CFG_CHSEL0_TEMP 192 #define AM_HAL_ADC_SLOT_CHSEL_VSS AM_REG_ADC_SL0CFG_CHSEL0_VSS 193 #define AM_HAL_ADC_SLOT_CHSEL_VBATT AM_REG_ADC_SL0CFG_CHSEL0_BATT 194 195 // Window enable. 196 #define AM_HAL_ADC_SLOT_WINDOW_EN AM_REG_ADC_SL0CFG_WCEN0(1) 197 198 // Enable the slot. 199 #define AM_HAL_ADC_SLOT_ENABLE AM_REG_ADC_SL0CFG_SLEN0(1) 200 //! @} 201 202 //***************************************************************************** 203 // 204 //! @name Interrupt Status Bits 205 //! @brief Interrupt Status Bits for enable/disble use 206 //! 207 //! These macros may be used to enable an individual ADC interrupt cause. 208 //! @{ 209 // 210 //***************************************************************************** 211 #define AM_HAL_ADC_INT_WCINC AM_REG_ADC_INTEN_WCINC(1) 212 #define AM_HAL_ADC_INT_WCEXC AM_REG_ADC_INTEN_WCEXC(1) 213 #define AM_HAL_ADC_INT_FIFOOVR2 AM_REG_ADC_INTEN_FIFOOVR2(1) 214 #define AM_HAL_ADC_INT_FIFOOVR1 AM_REG_ADC_INTEN_FIFOOVR1(1) 215 #define AM_HAL_ADC_INT_SCNCMP AM_REG_ADC_INTEN_SCNCMP(1) 216 #define AM_HAL_ADC_INT_CNVCMP AM_REG_ADC_INTEN_CNVCMP(1) 217 //! @} 218 219 //***************************************************************************** 220 // 221 //! @name Temperature Trim Value Locations 222 //! @brief Temperature calibration cofficients are stored in readable space. 223 //! 224 //! These macros are used to access the temperature trim values in readable 225 //! space. 226 //! @{ 227 // 228 //***************************************************************************** 229 #define AM_HAL_ADC_CALIB_TEMP_ADDR (0x50023010) 230 #define AM_HAL_ADC_CALIB_AMBIENT_ADDR (0x50023014) 231 #define AM_HAL_ADC_CALIB_ADC_OFFSET_ADDR (0x50023018) 232 233 // 234 // Default coefficients (used when trims not provided): 235 // TEMP_DEFAULT = Temperature in deg K (e.g. 299.5 - 273.15 = 26.35) 236 // AMBIENT_DEFAULT = Voltage measurement at default temperature. 237 // OFFSET_DEFAULT = Default ADC offset at 1v. 238 // 239 #define AM_HAL_ADC_CALIB_TEMP_DEFAULT (299.5F) 240 #define AM_HAL_ADC_CALIB_AMBIENT_DEFAULT (1.02809F) 241 #define AM_HAL_ADC_CALIB_ADC_OFFSET_DEFAULT (-0.004281F) 242 //! @} 243 244 //***************************************************************************** 245 // 246 //! @brief Configuration structure for the ADC. 247 // 248 //***************************************************************************** 249 typedef struct 250 { 251 //! Select the ADC Clock source using one of the clock source macros. 252 uint32_t ui32Clock; 253 254 //! Select the ADC trigger source using a trigger source macro. 255 uint32_t ui32TriggerConfig; 256 257 //! Use a macro to select the ADC reference voltage. 258 uint32_t ui32Reference; 259 260 //! Use a macro to decide whether to disable clocks between samples. 261 uint32_t ui32ClockMode; 262 263 //! Use a macro to select the ADC power mode. 264 uint32_t ui32PowerMode; 265 266 //! Select whether the ADC will re-trigger based on a signal from timer 3. 267 uint32_t ui32Repeat; 268 } 269 am_hal_adc_config_t; 270 271 //***************************************************************************** 272 // 273 //! @brief ADC Fifo Read macros 274 //! 275 //! These are helper macros for interpreting FIFO data. Each ADC FIFO entry 276 //! contains information about the slot number and the FIFO depth alongside the 277 //! current sample. These macros perform the correct masking and shifting to 278 //! read those values. 279 //! 280 //! The SAMPLE and FULL_SAMPLE options refer to the fractional part of averaged 281 //! samples. If you are not using hardware averaging or don't need the 282 //! fractional part of the ADC sample, you should just use 283 //! AM_HAL_ADC_FIFO_SAMPLE. 284 //! 285 //! If you do need the fractional part, use AM_HAL_ADC_FIFO_FULL_SAMPLE. This 286 //! macro will keep six bits of precision past the decimal point. Depending on 287 //! the number of averaged samples, anywhere between 1 and 6 of these bits will 288 //! be valid. Please consult the datasheet to find out how many bits of data 289 //! are valid for your chosen averaging settings. 290 //! 291 //! @{ 292 // 293 //***************************************************************************** 294 #define AM_HAL_ADC_FIFO_SAMPLE(value) \ 295 ((((value) & AM_REG_ADC_FIFO_DATA_M) >> AM_REG_ADC_FIFO_DATA_S) >> 6) 296 297 #define AM_HAL_ADC_FIFO_FULL_SAMPLE(value) \ 298 (((value) & AM_REG_ADC_FIFO_DATA_M) >> AM_REG_ADC_FIFO_DATA_S ) 299 300 #define AM_HAL_ADC_FIFO_SLOT(value) \ 301 (((value) & AM_REG_ADC_FIFO_SLOTNUM_M) >> AM_REG_ADC_FIFO_SLOTNUM_S) 302 303 #define AM_HAL_ADC_FIFO_COUNT(value) \ 304 (((value) & AM_REG_ADC_FIFO_COUNT_M) >> AM_REG_ADC_FIFO_COUNT_S) 305 //! @} 306 307 #ifdef __cplusplus 308 extern "C" 309 { 310 #endif 311 312 //***************************************************************************** 313 // 314 // External function definitions 315 // 316 //***************************************************************************** 317 extern void am_hal_adc_config(am_hal_adc_config_t *psConfig); 318 extern void am_hal_adc_window_set(uint32_t ui32Upper, uint32_t ui32Lower); 319 extern void am_hal_adc_slot_config(uint32_t ui32SlotNumber, 320 uint32_t ui32SlotConfig); 321 322 extern uint32_t am_hal_adc_fifo_peek(void); 323 extern uint32_t am_hal_adc_fifo_pop(void); 324 325 extern void am_hal_adc_trigger(void); 326 extern void am_hal_adc_enable(void); 327 extern void am_hal_adc_disable(void); 328 extern void am_hal_adc_int_enable(uint32_t ui32Interrupt); 329 extern uint32_t am_hal_adc_int_enable_get(void); 330 extern void am_hal_adc_int_disable(uint32_t ui32Interrupt); 331 extern void am_hal_adc_int_clear(uint32_t ui32Interrupt); 332 extern void am_hal_adc_int_set(uint32_t ui32Interrupt); 333 extern uint32_t am_hal_adc_int_status_get(bool bEnabledOnly); 334 extern float am_hal_adc_volts_to_celsius(float fVoltage); 335 extern void am_hal_adc_temp_trims_get(float * pfTemp, float * pfVoltage, float * pfOffsetV); 336 337 #ifdef __cplusplus 338 } 339 #endif 340 341 #endif // AM_HAL_ADC_H 342 343 //***************************************************************************** 344 // 345 // End Doxygen group. 346 //! @} 347 // 348 //***************************************************************************** 349