Patched version of nrf51822 FOTA compatible driver, with GPTIO disabled, as it clashed with the mbed definitions...

Fork of nRF51822 by Nordic Semiconductor

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers nrf_gpio.h Source File

nrf_gpio.h

00001 #ifndef NRF_GPIO_H__
00002 #define NRF_GPIO_H__
00003 
00004 #include "nrf51.h"
00005 #include "nrf51_bitfields.h"
00006 
00007 /**
00008  * @defgroup nrf_gpio GPIO abstraction
00009  * @{
00010  * @ingroup nrf_drivers
00011  * @brief GPIO pin abstraction and port abstraction for reading and writing byte-wise to GPIO ports.
00012  *
00013  * Here, the GPIO ports are defined as follows:
00014  * - Port 0 -> pin 0-7
00015  * - Port 1 -> pin 8-15
00016  * - Port 2 -> pin 16-23
00017  * - Port 3 -> pin 24-31
00018  */
00019 
00020 /**
00021  * @enum nrf_gpio_port_dir_t
00022  * @brief Enumerator used for setting the direction of a GPIO port.
00023  */
00024 typedef enum
00025 {
00026     NRF_GPIO_PORT_DIR_OUTPUT,       ///<  Output
00027     NRF_GPIO_PORT_DIR_INPUT         ///<  Input
00028 } nrf_gpio_port_dir_t;
00029 
00030 /**
00031  * @enum nrf_gpio_pin_dir_t
00032  * Pin direction definitions.
00033  */
00034 typedef enum
00035 {
00036     NRF_GPIO_PIN_DIR_INPUT,   ///< Input
00037     NRF_GPIO_PIN_DIR_OUTPUT   ///< Output
00038 } nrf_gpio_pin_dir_t;
00039 
00040 /**
00041  * @enum nrf_gpio_port_select_t
00042  * @brief Enumerator used for selecting between port 0 - 3.
00043  */
00044 typedef enum
00045 {
00046     NRF_GPIO_PORT_SELECT_PORT0 = 0,           ///<  Port 0 (GPIO pin 0-7)
00047     NRF_GPIO_PORT_SELECT_PORT1,               ///<  Port 1 (GPIO pin 8-15)
00048     NRF_GPIO_PORT_SELECT_PORT2,               ///<  Port 2 (GPIO pin 16-23)
00049     NRF_GPIO_PORT_SELECT_PORT3,               ///<  Port 3 (GPIO pin 24-31)
00050 } nrf_gpio_port_select_t;
00051 
00052 /**
00053  * @enum nrf_gpio_pin_pull_t
00054  * @brief Enumerator used for selecting the pin to be pulled down or up at the time of pin configuration
00055  */
00056 typedef enum
00057 {
00058     NRF_GPIO_PIN_NOPULL   = GPIO_PIN_CNF_PULL_Disabled,                 ///<  Pin pullup resistor disabled
00059     NRF_GPIO_PIN_PULLDOWN = GPIO_PIN_CNF_PULL_Pulldown,                 ///<  Pin pulldown resistor enabled
00060     NRF_GPIO_PIN_PULLUP   = GPIO_PIN_CNF_PULL_Pullup,                   ///<  Pin pullup resistor enabled
00061 } nrf_gpio_pin_pull_t;
00062 
00063 /**
00064  * @enum nrf_gpio_pin_sense_t
00065  * @brief Enumerator used for selecting the pin to sense high or low level on the pin input.
00066  */
00067 typedef enum
00068 {
00069     NRF_GPIO_PIN_NOSENSE    = GPIO_PIN_CNF_SENSE_Disabled,              ///<  Pin sense level disabled.
00070     NRF_GPIO_PIN_SENSE_LOW  = GPIO_PIN_CNF_SENSE_Low,                   ///<  Pin sense low level.
00071     NRF_GPIO_PIN_SENSE_HIGH = GPIO_PIN_CNF_SENSE_High,                  ///<  Pin sense high level.
00072 } nrf_gpio_pin_sense_t;
00073 
00074 /**
00075  * @brief Function for configuring the GPIO pin range as outputs with normal drive strength.
00076  *        This function can be used to configure pin range as simple output with gate driving GPIO_PIN_CNF_DRIVE_S0S1 (normal cases).
00077  *
00078  * @param pin_range_start specifies the start number (inclusive) in the range of pin numbers to be configured (allowed values 0-30)
00079  *
00080  * @param pin_range_end specifies the end number (inclusive) in the range of pin numbers to be configured (allowed values 0-30)
00081  *
00082  * @note For configuring only one pin as output use @ref nrf_gpio_cfg_output
00083  *       Sense capability on the pin is disabled, and input is disconnected from the buffer as the pins are configured as output.
00084  */
00085 static __INLINE void nrf_gpio_range_cfg_output(uint32_t pin_range_start, uint32_t pin_range_end)
00086 {
00087     /*lint -e{845} // A zero has been given as right argument to operator '|'" */
00088     for (; pin_range_start <= pin_range_end; pin_range_start++)
00089     {
00090         NRF_GPIO->PIN_CNF[pin_range_start] = (GPIO_PIN_CNF_SENSE_Disabled << GPIO_PIN_CNF_SENSE_Pos)
00091                                         | (GPIO_PIN_CNF_DRIVE_S0S1 << GPIO_PIN_CNF_DRIVE_Pos)
00092                                         | (GPIO_PIN_CNF_PULL_Disabled << GPIO_PIN_CNF_PULL_Pos)
00093                                         | (GPIO_PIN_CNF_INPUT_Disconnect << GPIO_PIN_CNF_INPUT_Pos)
00094                                         | (GPIO_PIN_CNF_DIR_Output << GPIO_PIN_CNF_DIR_Pos);
00095     }
00096 }
00097 
00098 /**
00099  * @brief Function for configuring the GPIO pin range as inputs with given initial value set, hiding inner details.
00100  *        This function can be used to configure pin range as simple input.
00101  *
00102  * @param pin_range_start specifies the start number (inclusive) in the range of pin numbers to be configured (allowed values 0-30)
00103  *
00104  * @param pin_range_end specifies the end number (inclusive) in the range of pin numbers to be configured (allowed values 0-30)
00105  *
00106  * @param pull_config State of the pin range pull resistor (no pull, pulled down or pulled high)
00107  *
00108  * @note  For configuring only one pin as input use @ref nrf_gpio_cfg_input
00109  *        Sense capability on the pin is disabled, and input is connected to buffer so that the GPIO->IN register is readable
00110  */
00111 static __INLINE void nrf_gpio_range_cfg_input(uint32_t pin_range_start, uint32_t pin_range_end, nrf_gpio_pin_pull_t pull_config)
00112 {
00113     /*lint -e{845} // A zero has been given as right argument to operator '|'" */
00114     for (; pin_range_start <= pin_range_end; pin_range_start++)
00115     {
00116         NRF_GPIO->PIN_CNF[pin_range_start] = (GPIO_PIN_CNF_SENSE_Disabled << GPIO_PIN_CNF_SENSE_Pos)
00117                                         | (GPIO_PIN_CNF_DRIVE_S0S1 << GPIO_PIN_CNF_DRIVE_Pos)
00118                                         | (pull_config << GPIO_PIN_CNF_PULL_Pos)
00119                                         | (GPIO_PIN_CNF_INPUT_Connect << GPIO_PIN_CNF_INPUT_Pos)
00120                                         | (GPIO_PIN_CNF_DIR_Input << GPIO_PIN_CNF_DIR_Pos);
00121     }
00122 }
00123 
00124 /**
00125  * @brief Function for configuring the given GPIO pin number as output with given initial value set, hiding inner details.
00126  *        This function can be used to configure pin range as simple input with gate driving GPIO_PIN_CNF_DRIVE_S0S1 (normal cases).
00127  *
00128  * @param pin_number specifies the pin number of gpio pin numbers to be configured (allowed values 0-30)
00129  *
00130  * @note  Sense capability on the pin is disabled, and input is disconnected from the buffer as the pins are configured as output.
00131  */
00132 static __INLINE void nrf_gpio_cfg_output(uint32_t pin_number)
00133 {
00134     /*lint -e{845} // A zero has been given as right argument to operator '|'" */
00135     NRF_GPIO->PIN_CNF[pin_number] = (GPIO_PIN_CNF_SENSE_Disabled << GPIO_PIN_CNF_SENSE_Pos)
00136                                             | (GPIO_PIN_CNF_DRIVE_S0S1 << GPIO_PIN_CNF_DRIVE_Pos)
00137                                             | (GPIO_PIN_CNF_PULL_Disabled << GPIO_PIN_CNF_PULL_Pos)
00138                                             | (GPIO_PIN_CNF_INPUT_Disconnect << GPIO_PIN_CNF_INPUT_Pos)
00139                                             | (GPIO_PIN_CNF_DIR_Output << GPIO_PIN_CNF_DIR_Pos);
00140 }
00141 
00142 /**
00143  * @brief Function for configuring the given GPIO pin number as input with given initial value set, hiding inner details.
00144  *        This function can be used to configure pin range as simple input with gate driving GPIO_PIN_CNF_DRIVE_S0S1 (normal cases).
00145  *
00146  * @param pin_number specifies the pin number of gpio pin numbers to be configured (allowed values 0-30)
00147  *
00148  * @param pull_config State of the pin range pull resistor (no pull, pulled down or pulled high)
00149  *
00150  * @note  Sense capability on the pin is disabled, and input is connected to buffer so that the GPIO->IN register is readable
00151  */
00152 static __INLINE void nrf_gpio_cfg_input(uint32_t pin_number, nrf_gpio_pin_pull_t pull_config)
00153 {
00154     /*lint -e{845} // A zero has been given as right argument to operator '|'" */
00155     NRF_GPIO->PIN_CNF[pin_number] = (GPIO_PIN_CNF_SENSE_Disabled << GPIO_PIN_CNF_SENSE_Pos)
00156                                         | (GPIO_PIN_CNF_DRIVE_S0S1 << GPIO_PIN_CNF_DRIVE_Pos)
00157                                         | (pull_config << GPIO_PIN_CNF_PULL_Pos)
00158                                         | (GPIO_PIN_CNF_INPUT_Connect << GPIO_PIN_CNF_INPUT_Pos)
00159                                         | (GPIO_PIN_CNF_DIR_Input << GPIO_PIN_CNF_DIR_Pos);
00160 }
00161 
00162 /**
00163  * @brief Function for configuring the given GPIO pin number as input with given initial value set, hiding inner details.
00164  *        This function can be used to configure pin range as simple input with gate driving GPIO_PIN_CNF_DRIVE_S0S1 (normal cases).
00165  *        Sense capability on the pin is configurable, and input is connected to buffer so that the GPIO->IN register is readable.
00166  *
00167  * @param pin_number specifies the pin number of gpio pin numbers to be configured (allowed values 0-30).
00168  *
00169  * @param pull_config state of the pin pull resistor (no pull, pulled down or pulled high).
00170  *
00171  * @param sense_config sense level of the pin (no sense, sense low or sense high).
00172  */
00173 static __INLINE void nrf_gpio_cfg_sense_input(uint32_t pin_number, nrf_gpio_pin_pull_t pull_config, nrf_gpio_pin_sense_t sense_config)
00174 {
00175     /*lint -e{845} // A zero has been given as right argument to operator '|'" */
00176     NRF_GPIO->PIN_CNF[pin_number] = (sense_config << GPIO_PIN_CNF_SENSE_Pos)
00177                                         | (GPIO_PIN_CNF_DRIVE_S0S1 << GPIO_PIN_CNF_DRIVE_Pos)
00178                                         | (pull_config << GPIO_PIN_CNF_PULL_Pos)
00179                                         | (GPIO_PIN_CNF_INPUT_Connect << GPIO_PIN_CNF_INPUT_Pos)
00180                                         | (GPIO_PIN_CNF_DIR_Input << GPIO_PIN_CNF_DIR_Pos);
00181 }
00182 
00183 /**
00184  * @brief Function for setting the direction for a GPIO pin.
00185  *
00186  * @param pin_number specifies the pin number [0:31] for which to
00187  * set the direction.
00188  *
00189  * @param direction specifies the direction
00190  */
00191 static __INLINE void nrf_gpio_pin_dir_set(uint32_t pin_number, nrf_gpio_pin_dir_t direction)
00192 {
00193     if(direction == NRF_GPIO_PIN_DIR_INPUT)
00194     {
00195         NRF_GPIO->PIN_CNF[pin_number] =
00196           (GPIO_PIN_CNF_SENSE_Disabled << GPIO_PIN_CNF_SENSE_Pos)
00197         | (GPIO_PIN_CNF_DRIVE_S0S1 << GPIO_PIN_CNF_DRIVE_Pos)
00198         | (GPIO_PIN_CNF_PULL_Disabled << GPIO_PIN_CNF_PULL_Pos)
00199         | (GPIO_PIN_CNF_INPUT_Connect << GPIO_PIN_CNF_INPUT_Pos)
00200         | (GPIO_PIN_CNF_DIR_Input << GPIO_PIN_CNF_DIR_Pos);
00201     }
00202     else
00203     {
00204         NRF_GPIO->DIRSET = (1UL << pin_number);
00205     }
00206 }
00207 
00208 /**
00209  * @brief Function for setting a GPIO pin.
00210  *
00211  * Note that the pin must be configured as an output for this
00212  * function to have any effect.
00213  *
00214  * @param pin_number specifies the pin number [0:31] to
00215  * set.
00216  */
00217 static __INLINE void nrf_gpio_pin_set(uint32_t pin_number)
00218 {
00219     NRF_GPIO->OUTSET = (1UL << pin_number);
00220 }
00221 
00222 /**
00223  * @brief Function for clearing a GPIO pin.
00224  *
00225  * Note that the pin must be configured as an output for this
00226  * function to have any effect.
00227  *
00228  * @param pin_number specifies the pin number [0:31] to
00229  * clear.
00230  */
00231 static __INLINE void nrf_gpio_pin_clear(uint32_t pin_number)
00232 {
00233     NRF_GPIO->OUTCLR = (1UL << pin_number);
00234 }
00235 
00236 /**
00237  * @brief Function for toggling a GPIO pin.
00238  *
00239  * Note that the pin must be configured as an output for this
00240  * function to have any effect.
00241  *
00242  * @param pin_number specifies the pin number [0:31] to
00243  * toggle.
00244  */
00245 static __INLINE void nrf_gpio_pin_toggle(uint32_t pin_number)
00246 {
00247     const uint32_t pin_bit   = 1UL << pin_number;
00248     const uint32_t pin_state = ((NRF_GPIO->OUT >> pin_number) & 1UL);
00249     
00250     if (pin_state == 0)
00251     {
00252         // Current state low, set high.
00253         NRF_GPIO->OUTSET = pin_bit;        
00254     }
00255     else
00256     {
00257         // Current state high, set low.    
00258         NRF_GPIO->OUTCLR = pin_bit;       
00259     }
00260 }
00261 
00262 /**
00263  * @brief Function for writing a value to a GPIO pin.
00264  *
00265  * Note that the pin must be configured as an output for this
00266  * function to have any effect.
00267  *
00268  * @param pin_number specifies the pin number [0:31] to
00269  * write.
00270  *
00271  * @param value specifies the value to be written to the pin.
00272  * @arg 0 clears the pin
00273  * @arg >=1 sets the pin.
00274  */
00275 static __INLINE void nrf_gpio_pin_write(uint32_t pin_number, uint32_t value)
00276 {
00277     if (value == 0)
00278     {
00279         nrf_gpio_pin_clear(pin_number);
00280     }
00281     else
00282     {
00283         nrf_gpio_pin_set(pin_number);
00284     }
00285 }
00286 
00287 /**
00288  * @brief Function for reading the input level of a GPIO pin.
00289  *
00290  * Note that the pin must have input connected for the value
00291  * returned from this function to be valid.
00292  *
00293  * @param pin_number specifies the pin number [0:31] to
00294  * read.
00295  *
00296  * @return
00297  * @retval 0 if the pin input level is low.
00298  * @retval 1 if the pin input level is high.
00299  * @retval > 1 should never occur.
00300  */
00301 static __INLINE uint32_t nrf_gpio_pin_read(uint32_t pin_number)
00302 {
00303     return  ((NRF_GPIO->IN >> pin_number) & 1UL);
00304 }
00305 
00306 /**
00307  * @brief Generic function for writing a single byte of a 32 bit word at a given
00308  * address.
00309  *
00310  * This function should not be called from outside the nrf_gpio
00311  * abstraction layer.
00312  *
00313  * @param word_address is the address of the word to be written.
00314  *
00315  * @param byte_no is the the word byte number (0-3) to be written.
00316  *
00317  * @param value is the value to be written to byte "byte_no" of word
00318  * at address "word_address"
00319  */
00320 static __INLINE void nrf_gpio_word_byte_write(volatile uint32_t * word_address, uint8_t byte_no, uint8_t value)
00321 {
00322     *((volatile uint8_t*)(word_address) + byte_no) = value;
00323 }
00324 
00325 /**
00326  * @brief Generic function for reading a single byte of a 32 bit word at a given
00327  * address.
00328  *
00329  * This function should not be called from outside the nrf_gpio
00330  * abstraction layer.
00331  *
00332  * @param word_address is the address of the word to be read.
00333  *
00334  * @param byte_no is the the byte number (0-3) of the word to be read.
00335  *
00336  * @return byte "byte_no" of word at address "word_address".
00337  */
00338 static __INLINE uint8_t nrf_gpio_word_byte_read(const volatile uint32_t* word_address, uint8_t byte_no)
00339 {
00340     return (*((const volatile uint8_t*)(word_address) + byte_no));
00341 }
00342 
00343 /**
00344  * @brief Function for setting the direction of a port.
00345  *
00346  * @param port is the port for which to set the direction.
00347  *
00348  * @param dir direction to be set for this port.
00349  */
00350 static __INLINE void nrf_gpio_port_dir_set(nrf_gpio_port_select_t port, nrf_gpio_port_dir_t dir)
00351 {
00352     if (dir == NRF_GPIO_PORT_DIR_OUTPUT)
00353     {
00354         nrf_gpio_word_byte_write(&NRF_GPIO->DIRSET, port, 0xFF);
00355     }
00356     else
00357     {
00358         nrf_gpio_range_cfg_input(port*8, (port+1)*8-1, NRF_GPIO_PIN_NOPULL);
00359     }
00360 }
00361 
00362 /**
00363  * @brief Function for reading a GPIO port.
00364  *
00365  * @param port is the port to read.
00366  *
00367  * @return the input value on this port.
00368  */
00369 static __INLINE uint8_t nrf_gpio_port_read(nrf_gpio_port_select_t port)
00370 {
00371     return nrf_gpio_word_byte_read(&NRF_GPIO->IN, port);
00372 }
00373 
00374 /**
00375  * @brief Function for writing to a GPIO port.
00376  *
00377  * @param port is the port to write.
00378  *
00379  * @param value is the value to write to this port.
00380  *
00381  * @sa nrf_gpio_port_dir_set()
00382  */
00383 static __INLINE void nrf_gpio_port_write(nrf_gpio_port_select_t port, uint8_t value)
00384 {
00385     nrf_gpio_word_byte_write(&NRF_GPIO->OUT, port, value);
00386 }
00387 
00388 /**
00389  * @brief Function for setting individual pins on GPIO port.
00390  *
00391  * @param port is the port for which to set the pins.
00392  *
00393  * @param set_mask is a mask specifying which pins to set. A bit
00394  * set to 1 indicates that the corresponding port pin shall be
00395  * set.
00396  *
00397  * @sa nrf_gpio_port_dir_set()
00398  */
00399 static __INLINE void nrf_gpio_port_set(nrf_gpio_port_select_t port, uint8_t set_mask)
00400 {
00401     nrf_gpio_word_byte_write(&NRF_GPIO->OUTSET, port, set_mask);
00402 }
00403 
00404 /**
00405  * @brief Function for clearing individual pins on GPIO port.
00406  *
00407  * @param port is the port for which to clear the pins.
00408  *
00409  * @param clr_mask is a mask specifying which pins to clear. A bit
00410  * set to 1 indicates that the corresponding port pin shall be
00411  * cleared.
00412  *
00413  * @sa nrf_gpio_port_dir_set()
00414  */
00415 static __INLINE void nrf_gpio_port_clear(nrf_gpio_port_select_t port, uint8_t clr_mask)
00416 {
00417     nrf_gpio_word_byte_write(&NRF_GPIO->OUTCLR, port, clr_mask);
00418 }
00419 
00420 /** @} */
00421 
00422 #endif