ADC12 Problem

Hi, I downloaded a sample program illustrating the use of the ADC12 from the TI website onto my MSP430F169. I connected the input voltage to the selected pin, and watched the the variable storing the converted values “results”. Unfortunately, the values sort of just waver around 2000 and never really change regardless of the input voltage. Why is this?? I’ll include the code I’m using below, and i would really appreciate some help!

//******************************************************************************

// MSP-FET430P140 Demo - ADC12, Repeated Single Channel Conversions

//

// Description: This example shows how to perform repeated conversions on a

// single channel using “repeat-single-channel” mode. AVcc is used for the

// reference and repeated conversions are performed on Channel A0. Each

// conversion result is moved to an 8-element array called results. Test by

// applying a voltage to channel A0, then running. To view the conversion results

// open a watch window and view ‘results.’

// This can run even in LPM4 mode as ADC has its own clock

//

// MSP430F149

// ---------------

// | |

// Vin -->|P6.0/A0 |

// | |

//

//

// M. Mitchell

// Texas Instruments Inc.

// Feb 2005

// Built with IAR Embedded Workbench Version: 3.21A

//******************************************************************************

#include <msp430x16x.h>

#define Num_of_Results 100

static unsigned int results[Num_of_Results]; // Needs to be global in this

// example. Otherwise, the

// compiler removes it because it

// is not used for anything.

void main(void)

{

WDTCTL = WDTPW+WDTHOLD; // Stop watchdog timer

P1DIR = 0x03;

P1OUT = BIT0; // Turn on LED1

P6SEL |= 0x02; // Enable A/D channel A0

ADC12CTL0 = ADC12ON + SHT0_8 + MSC + REF2_5V + REFON ; // Turn on ADC12, set sampling time, multiple samples

ADC12CTL1 = SHP + CONSEQ_2; // Use sampling timer, set mode

ADC12IE = 0x01; // Enable ADC12IFG.0

ADC12CTL0 |= ENC; // Enable conversions

ADC12CTL0 |= ADC12SC; // Start conversion

_BIS_SR(LPM0_bits + GIE); // Enter LPM0,Enable interrupts

}

#pragma vector=ADC_VECTOR

__interrupt void ADC12ISR (void)

{

static unsigned int index = 0;

results[index] = ADC12MEM0; // Move results

index = (index+1)%Num_of_Results; // Increment results index, modulo

}

Do you ever initialize the ADC12MCTLx register(s)? You need to set up the ADC12MCTL0 register to tell the ADC what it should write into the corresponding ADC12MEM0 location (which channel, what reference voltage, etc). I think they’re supposed to be set to 0 on powerup, but it can’t hurt to initialize them explicitly.

Thanks, I have initialized the ADCMCTLx registers; however now the readings in the “results” array remain absolutely constant, despite any changes in the input voltage. Do you have any other suggestions?

revised code:

//******************************************************************************

// MSP-FET430P140 Demo - ADC12, Repeated Single Channel Conversions

//

// Description: This example shows how to perform repeated conversions on a

// single channel using “repeat-single-channel” mode. AVcc is used for the

// reference and repeated conversions are performed on Channel A0. Each

// conversion result is moved to an 8-element array called results. Test by

// applying a voltage to channel A0, then running. To view the conversion results

// open a watch window and view ‘results.’

// This can run even in LPM4 mode as ADC has its own clock

//

// MSP430F149

// ---------------

// | |

// Vin -->|P6.0/A0 |

// | |

//

//

// M. Mitchell

// Texas Instruments Inc.

// Feb 2005

// Built with IAR Embedded Workbench Version: 3.21A

//******************************************************************************

#include <msp430x14x.h>

#define Num_of_Results 20

#define LED1_ON P1OUT &= ~BIT0

#define LED1_OFF P1OUT |= BIT0

static unsigned int results[Num_of_Results]; // Needs to be global in this

static unsigned int results2[Num_of_Results]; // example. Otherwise, the

// compiler removes it because it

// is not used for anything.

void main(void)

{

P1DIR = 0x03;

LED1_ON;

WDTCTL = WDTPW+WDTHOLD; // Stop watchdog timer

P6SEL |= 0x03; // Enable A/D channel A0

ADC12CTL0 = ADC12ON+SHT0_8+MSC; // Turn on ADC12, set sampling time_1

ADC12CTL1 = SHP+CONSEQ_2; // Use sampling timer, set mode

ADC12MCTL1 = INCH_1 + SREF_1; // DR

ADC12MCTL0 = INCH_0 + SREF_1; // DR

ADC12IE = 0x01; // Enable ADC12IFG.0

ADC12CTL0 |= ENC; // Enable conversions

ADC12CTL0 |= ADC12SC; // Start conversion

_BIS_SR(LPM0_bits + GIE); // Enter LPM0,Enable interrupts

}

#pragma vector=ADC_VECTOR

__interrupt void ADC12ISR (void)

{

static unsigned int index = 0;

results[index] = ADC12MEM0; // Move results

results2[index] = ADC12MEM1; // DR

index = (index+1)%Num_of_Results; // Increment results index, modulo

}

DR:
Thanks, I have initialized the ADCMCTLx registers; however now the readings in the “results” array remain absolutely constant, despite any changes in the input voltage. Do you have any other suggestions?

revised code:

//******************************************************************************

// MSP-FET430P140 Demo - ADC12, Repeated Single Channel Conversions

//

// Description: This example shows how to perform repeated conversions on a

// single channel using “repeat-single-channel” mode. AVcc is used for the

// reference and repeated conversions are performed on Channel A0. Each

// conversion result is moved to an 8-element array called results. Test by

// applying a voltage to channel A0, then running. To view the conversion results

// open a watch window and view ‘results.’

// This can run even in LPM4 mode as ADC has its own clock

//

// MSP430F149

// ---------------

// | |

// Vin -->|P6.0/A0 |

// | |

//

//

// M. Mitchell

// Texas Instruments Inc.

// Feb 2005

// Built with IAR Embedded Workbench Version: 3.21A

//******************************************************************************

#include <msp430x14x.h>

#define Num_of_Results 20

#define LED1_ON P1OUT &= ~BIT0

#define LED1_OFF P1OUT |= BIT0

static unsigned int results[Num_of_Results]; // Needs to be global in this

static unsigned int results2[Num_of_Results]; // example. Otherwise, the

// compiler removes it because it

// is not used for anything.

void main(void)

{

P1DIR = 0x03;

LED1_ON;

WDTCTL = WDTPW+WDTHOLD; // Stop watchdog timer

P6SEL |= 0x03; // Enable A/D channel A0

ADC12CTL0 = ADC12ON+SHT0_8+MSC; // Turn on ADC12, set sampling time_1

ADC12CTL1 = SHP+CONSEQ_2; // Use sampling timer, set mode

ADC12MCTL1 = INCH_1 + SREF_1; // DR

ADC12MCTL0 = INCH_0 + SREF_1; // DR

ADC12IE = 0x01; // Enable ADC12IFG.0

ADC12CTL0 |= ENC; // Enable conversions

ADC12CTL0 |= ADC12SC; // Start conversion

_BIS_SR(LPM0_bits + GIE); // Enter LPM0,Enable interrupts

}

#pragma vector=ADC_VECTOR

__interrupt void ADC12ISR (void)

{

static unsigned int index = 0;

results[index] = ADC12MEM0; // Move results

results2[index] = ADC12MEM1; // DR

index = (index+1)%Num_of_Results; // Increment results index, modulo

}

first of all conseq_2 is repeat SINGLE channel, you need to use CONSEQ_3

second when using a sequence of channels the last channel MUST be identified

ADC12MCTL1 = INCH_1 + SREF_1+ EOS;

third since you are using 2 channels you MUST enable the interrupt on both

ADC12IE = 0x03;

You are using athe internal ref you must turn it on

ADC12CTL0 |= (REF2_5V + REFON); // Enable 2.5v reference

Your modifying example programs without paying attention to details… You need to read the family manual much more closely…

sorry! i hadnt commented my changes too well… I actually DO want single channel repeated conversions, I’ve just been trying the input voltage on different pins (6.0 and 6.1) to see if that would make some sort of difference…But switching my input channels had no effect. sorry for the misunderstanding!

DR:
sorry! i hadnt commented my changes too well… I actually DO want single channel repeated conversions, I’ve just been trying the input voltage on different pins (6.0 and 6.1) to see if that would make some sort of difference…But switching my input channels had no effect. sorry for the misunderstanding!

well you are specifying the internal reference as the source so you MUST turn it on… also make sure you have the proper caps connected to the vref pins otheriwse all bets are off…

Thanks for your help! I have it working now!