1 /*
2  * Copyright (c) 2012 - 2023, Nordic Semiconductor ASA
3  * All rights reserved.
4  *
5  * SPDX-License-Identifier: BSD-3-Clause
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions are met:
9  *
10  * 1. Redistributions of source code must retain the above copyright notice, this
11  *    list of conditions and the following disclaimer.
12  *
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in the
15  *    documentation and/or other materials provided with the distribution.
16  *
17  * 3. Neither the name of the copyright holder nor the names of its
18  *    contributors may be used to endorse or promote products derived from this
19  *    software without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
22  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
25  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
26  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
27  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
28  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
29  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
30  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
31  * POSSIBILITY OF SUCH DAMAGE.
32  */
33 
34 #ifndef NRF_TEMP_H__
35 #define NRF_TEMP_H__
36 
37 #include <nrfx.h>
38 
39 #ifdef __cplusplus
40 extern "C" {
41 #endif
42 
43 /**
44 * @defgroup nrf_temp_hal TEMP HAL
45 * @{
46 * @ingroup nrf_temp
47 * @brief   Hardware access layer for managing the Temperature sensor (TEMP).
48 */
49 
50 /** @brief TEMP tasks. */
51 typedef enum
52 {
53     NRF_TEMP_TASK_START = offsetof(NRF_TEMP_Type, TASKS_START), /**< Start temperature measurement. */
54     NRF_TEMP_TASK_STOP  = offsetof(NRF_TEMP_Type, TASKS_STOP)   /**< Stop temperature measurement. */
55 } nrf_temp_task_t;
56 
57 /** @brief TEMP events. */
58 typedef enum
59 {
60     NRF_TEMP_EVENT_DATARDY = offsetof(NRF_TEMP_Type, EVENTS_DATARDY) /**< Temperature measurement complete, data ready. */
61 } nrf_temp_event_t;
62 
63 /** @brief TEMP interrupts. */
64 typedef enum
65 {
66     NRF_TEMP_INT_DATARDY_MASK = TEMP_INTENSET_DATARDY_Msk /**< Interrupt on DATARDY event.  */
67 } nrf_temp_int_mask_t;
68 
69 /**
70  * @brief Function for enabling specified interrupts.
71  *
72  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
73  * @param[in] mask  Mask of interrupts to be enabled.
74  */
75 NRF_STATIC_INLINE void nrf_temp_int_enable(NRF_TEMP_Type * p_reg, uint32_t mask);
76 
77 /**
78  * @brief Function for disabling specified interrupts.
79  *
80  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
81  * @param[in] mask  Mask of interrupts to be disabled.
82  */
83 NRF_STATIC_INLINE void nrf_temp_int_disable(NRF_TEMP_Type * p_reg, uint32_t mask);
84 
85 /**
86  * @brief Function for checking if the specified interrupts are enabled.
87  *
88  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
89  * @param[in] mask  Mask of interrupts to be checked.
90  *
91  * @return Mask of enabled interrupts.
92  */
93 NRF_STATIC_INLINE uint32_t nrf_temp_int_enable_check(NRF_TEMP_Type const * p_reg, uint32_t mask);
94 
95 /**
96  * @brief Function for getting the address of the specified TEMP task register.
97  *
98  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
99  * @param[in] task  Requested task.
100  *
101  * @return Address of the requested task register.
102  */
103 NRF_STATIC_INLINE uint32_t nrf_temp_task_address_get(NRF_TEMP_Type const * p_reg,
104                                                      nrf_temp_task_t       task);
105 
106 /**
107  * @brief Function for activating the specified TEMP task.
108  *
109  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
110  * @param[in] task  Task to be activated.
111  */
112 NRF_STATIC_INLINE void nrf_temp_task_trigger(NRF_TEMP_Type * p_reg, nrf_temp_task_t task);
113 
114 /**
115  * @brief Function for getting the address of the specified TEMP event register.
116  *
117  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
118  * @param[in] event Requested event.
119  *
120  * @return Address of the requested event register.
121  */
122 NRF_STATIC_INLINE uint32_t nrf_temp_event_address_get(NRF_TEMP_Type const * p_reg,
123                                                       nrf_temp_event_t      event);
124 
125 /**
126  * @brief Function for clearing the specified TEMP event.
127  *
128  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
129  * @param[in] event Event to clear.
130  */
131 NRF_STATIC_INLINE void nrf_temp_event_clear(NRF_TEMP_Type *  p_reg, nrf_temp_event_t event);
132 
133 /**
134  * @brief Function for getting the state of a specific event.
135  *
136  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
137  * @param[in] event Event to be checked.
138  *
139  * @retval true  The event has been generated.
140  * @retval false The event has not been generated.
141  */
142 NRF_STATIC_INLINE bool nrf_temp_event_check(NRF_TEMP_Type const * p_reg, nrf_temp_event_t event);
143 
144 /**
145  * @brief Function for getting the result of temperature measurement.
146  *
147  * @note Returned value is in 2's complement format, 0.25 °C steps
148  *
149  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
150  *
151  * @return Temperature value register contents.
152  */
153 NRF_STATIC_INLINE int32_t nrf_temp_result_get(NRF_TEMP_Type const * p_reg);
154 
155 #ifndef NRF_DECLARE_ONLY
156 
nrf_temp_int_enable(NRF_TEMP_Type * p_reg,uint32_t mask)157 NRF_STATIC_INLINE void nrf_temp_int_enable(NRF_TEMP_Type * p_reg, uint32_t mask)
158 {
159     p_reg->INTENSET = mask;
160 }
161 
nrf_temp_int_disable(NRF_TEMP_Type * p_reg,uint32_t mask)162 NRF_STATIC_INLINE void nrf_temp_int_disable(NRF_TEMP_Type * p_reg, uint32_t mask)
163 {
164     p_reg->INTENCLR = mask;
165 }
166 
nrf_temp_int_enable_check(NRF_TEMP_Type const * p_reg,uint32_t mask)167 NRF_STATIC_INLINE uint32_t nrf_temp_int_enable_check(NRF_TEMP_Type const * p_reg, uint32_t mask)
168 {
169     return p_reg->INTENSET & mask;
170 }
171 
nrf_temp_task_address_get(NRF_TEMP_Type const * p_reg,nrf_temp_task_t task)172 NRF_STATIC_INLINE uint32_t nrf_temp_task_address_get(NRF_TEMP_Type const * p_reg,
173                                                      nrf_temp_task_t       task)
174 {
175     return (uint32_t)((uint8_t *)p_reg + (uint32_t)task);
176 }
177 
nrf_temp_task_trigger(NRF_TEMP_Type * p_reg,nrf_temp_task_t task)178 NRF_STATIC_INLINE void nrf_temp_task_trigger(NRF_TEMP_Type * p_reg, nrf_temp_task_t task)
179 {
180     *(volatile uint32_t *)((uint8_t *)p_reg + (uint32_t)task) = 1;
181 }
182 
nrf_temp_event_address_get(NRF_TEMP_Type const * p_reg,nrf_temp_event_t event)183 NRF_STATIC_INLINE uint32_t nrf_temp_event_address_get(NRF_TEMP_Type const * p_reg,
184                                                       nrf_temp_event_t      event)
185 {
186     return (uint32_t)((uint8_t *)p_reg + (uint32_t)event);
187 }
188 
nrf_temp_event_clear(NRF_TEMP_Type * p_reg,nrf_temp_event_t event)189 NRF_STATIC_INLINE void nrf_temp_event_clear(NRF_TEMP_Type * p_reg, nrf_temp_event_t event)
190 {
191     *((volatile uint32_t *)((uint8_t *)p_reg + (uint32_t)event)) = 0;
192     nrf_event_readback((uint8_t *)p_reg + (uint32_t)event);
193 }
194 
nrf_temp_event_check(NRF_TEMP_Type const * p_reg,nrf_temp_event_t event)195 NRF_STATIC_INLINE bool nrf_temp_event_check(NRF_TEMP_Type const * p_reg, nrf_temp_event_t event)
196 {
197     return (bool)*((volatile uint32_t *)((uint8_t *)p_reg + (uint32_t)event));
198 }
199 
nrf_temp_result_get(NRF_TEMP_Type const * p_reg)200 NRF_STATIC_INLINE int32_t nrf_temp_result_get(NRF_TEMP_Type const * p_reg)
201 {
202     int32_t raw_measurement = p_reg->TEMP;
203 
204 #if defined(NRF51)
205     /* Apply workaround for the nRF51 series anomaly 28 - TEMP: Negative measured values are not represented correctly. */
206     if ((raw_measurement & 0x00000200) != 0)
207     {
208         raw_measurement |= 0xFFFFFC00UL;
209     }
210 #endif
211 
212     return raw_measurement;
213 }
214 
215 #endif // NRF_DECLARE_ONLY
216 
217 /** @} */
218 
219 #ifdef __cplusplus
220 }
221 #endif
222 
223 #endif // NRF_TEMP_H__
224