This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

Can't get a ADC result that makes sense

Hi,

I'm working on a simple ADC application where I sample using analog channel 1 and then read the value through the debugger. However my results are nonsense. I have connected a potmeter with VDD on the right pin, ground on the left and the analog input as the center pin. No matter which analog pin I connect the center potmeter pin to, i get a value around 0x50. I feel I have forgotten to set-up the analog input pin. It's like there's missing a connection between the input-pin and the ADC.

\#include <stdbool.h> 
\#include "nrf.h" 
\#include "nrf_delay.h" 
\#include "nrf_gpio.h" 


uint32_t result = 0;

/** Configures port 1 as output */
static void gpio_config(void)
{
  nrf_gpio_range_cfg_output(8, 15);
  nrf_gpio_port_write(NRF_GPIO_PORT_SELECT_PORT1, 0);

    nrf_gpio_cfg_input(20, NRF_GPIO_PIN_PULLUP);		//BUTTON 4
    nrf_gpio_cfg_output(23);						//LED 3
    nrf_gpio_cfg_output(24);						//LED 4

    //Interupt on button 4
    NVIC_EnableIRQ(GPIOTE_IRQn);
        NRF_GPIOTE->CONFIG[0] = (GPIOTE_CONFIG_POLARITY_HiToLo << GPIOTE_CONFIG_POLARITY_Pos)
                        | (20 << GPIOTE_CONFIG_PSEL_Pos)				//BUTTON 4
                        | (GPIOTE_CONFIG_MODE_Event << GPIOTE_CONFIG_MODE_Pos);
NRF_GPIOTE->INTENSET = GPIOTE_INTENSET_IN0_Set << GPIOTE_INTENSET_IN0_Pos;

}

void GPIOTE_IRQHandler(void)
{
    // Event causing the interrupt must be cleared.
    if ((NRF_GPIOTE->EVENTS_IN[0] == 1) &&
        (NRF_GPIOTE->INTENSET & GPIOTE_INTENSET_IN0_Msk))
    {
        NRF_GPIOTE->EVENTS_IN[0] = 0;
				nrf_gpio_pin_toggle(23);
				NRF_ADC->TASKS_START = 1;
    }
}

/** Configures and enables the ADC */
void ADC_init(void)
{	
/* Enable interrupt on ADC sample ready event*/		
    NRF_ADC->INTENSET = ADC_INTENSET_END_Msk;
    NVIC_EnableIRQ(ADC_IRQn);	


NRF_ADC->CONFIG	= (ADC_CONFIG_EXTREFSEL_None << ADC_CONFIG_EXTREFSEL_Pos) 										/* Bits 17..16 : No external reference. */
									| (ADC_CONFIG_PSEL_AnalogInput1 << ADC_CONFIG_PSEL_Pos)											/*!< Use analog input 1 as analog input. */
									| (ADC_CONFIG_REFSEL_SupplyOneThirdPrescaling << ADC_CONFIG_REFSEL_Pos)			/*!< Use VDD/3 */
									| (ADC_CONFIG_INPSEL_AnalogInputOneThirdPrescaling << ADC_CONFIG_INPSEL_Pos) 			/*!< Analog input specified by PSEL with 1/3 prescaling used as input for the conversion. */
									| (ADC_CONFIG_RES_8bit << ADC_CONFIG_RES_Pos);															/*!< 8 bit */

/* Enable ADC*/
NRF_ADC->ENABLE = ADC_ENABLE_ENABLE_Enabled;	
}

/* Interrupt handler for ADC data ready event */
void ADC_IRQHandler(void)
{
/* Clear dataready event */
  NRF_ADC->EVENTS_END = 0;	

  /* Write ADC result to port 1 */
 	//nrf_gpio_port_write(NRF_GPIO_PORT_SELECT_PORT1, NRF_ADC->RESULT); 
    nrf_gpio_pin_toggle(24);

    //Use the STOP task to save current. Workaround for PAN_028 rev1.2 anomaly 1.
  NRF_ADC->TASKS_STOP = 1;

    //Write result
    result = NRF_ADC->RESULT;  
}
  • How do I make the code look nice in the question btw? The above is pretty messy

  • Anything with 4 spaces in front is interpreted as code. So your code works, except the result is weird? (you can see pin 24 toggle?) It sounds like the ADC pin is floating.. are you sure you have connected the pot to the correct pin? (pin 27). Have you double checked with a multimeter on the pot to see if the voltage varies as expected?

  • My code is working and the LED's are toggling every time i press the button. I think the pin is floating too. You are mentioning pin 27 as being the right pin? I'm having a really hard time figuring out which pins are what. According to the user guide for the PCA10028 board P2 is the analog port and P2 contains P0.01 through P0.06.

  • First of all you need to figure out which pin ADC_CONFIG_PSEL_AnalogInput1 is. If you are using PCA10028 (nRF51 DK) you should check out the Product Specification for the nRF51422 chip: link. Scroll down to section 2.2.1.1 for a description of all the pins. You will see that pin 46, or "gpio" pin P0.27 is used as ADC/LPCOMP input 1. However, we also see that this pin is a connection pin for the external 32kHz crystal (!). If you also check the nRF51 DK User Guide, section 5.4, there is a note saying "P0.26 and P0.27 are by default used for the 32 kHz crystal and are not available on the connectors." So, unless you follow the guide to make them available, it is not physically possible to connect something to Analog Input 1.

    My advice would be to use a different ADC input, for example ADC_CONFIG_PSEL_AnalogInput2, which is connected to pin P0.01. (P0.01 is clearly marked on the board)

    The numbering can be a bit confusing, but remember to always check the datasheets, since the ADC input pins aren't really connected in a logical sequence

  • Thank you very much Vebjørn. I messed up the pins. It's pretty obvious after a good nights sleep and a big cup of coffee.

Related