I am going through Chapter 5 in the SoftBaugh MSP430 State Machine Programming book and am having trouble getting started. I have tried this twice now, deleting the project and starting over with the solution from the previous chapter, and then making the indicated changes.
The program runs up into the while loop, gets past the __low_power_mode_3
and will not continue after that, indicating that it never wakes from LPM3.
My instructor and I put an oscilloscope on pin 2.0 and 2.1 but we can't see any signal from ACLK. When I halt execution and look at the registers, I see that BCSCTL3 is showing a fault.
We have tried different boards (MSP430F2274 evaluation boards) and both with USBP and just connected to the AC adapter.
Here's my code:
main.c
#include "System.h"
#include "msp430x22x4.h"
#define TICK_DIVISOR 64
static __no_init int mMain_nCounter;
void InitializeHW (void);
void InitializeApps (void);
int main( void )
{
// Stop watchdog timer to prevent time out reset
WDTCTL = (WDTPW | WDTHOLD);
InitializeHW();
InitializeApps();
__enable_interrupt();
while(1){
__low_power_mode_3();
mMain_nCounter--; // <-- this never executes
if (mMain_nCounter > 0){
// count not expired yet
continue;
}
//restart the counter
mMain_nCounter = TICK_DIVISOR;
// twiddle the LED
P1OUT ^= (BIT0);
}
}
void InitializeHW( void )
{
System_InitializeHW();
}
void InitializeApps( void )
{
mMain_nCounter = TICK_DIVISOR;
}
system.c
#include "msp430x22x4.h"
#include "System.h"
#define TICK_DIVISOR 32
void System_InitializePorts( void );
void System_SetupACLK_VLO( void );
void System_SetupTimerA3( void );
void System_SetupWatchdogTimer( void );
void System_InitializeHW( void )
{
// Set 12.5 pF internal capacitance
BCSCTL3 = (XCAP_3);
System_InitializePorts();
// System_SetupACLK_VLO();
System_SetupTimerA3();
System_SetupWatchdogTimer();
}
void System_InitializePorts( void )
{
// Port1 initialization
// P1.0 - D1
// P1.1 - n/c
// P1.2 - n/c
// P1.3 - n/c
// P1.4 - n/c
// P1.5 - n/c
// P1.6 - n/c
// P1.7 - n/c
P1OUT = (0x00);
P1DIR = (0xFF);
P1SEL = (0x00);
// Port2 initialization
// P2.0 - ACLK or n/c
// P2.1 - SMCLK or n/c
// P2.2 - n/c
// P2.3 - n/c
// P2.4 - n/c
// P2.5 - n/c
// P2.6 - XIN or n/c
// P2.7 - XOUT or n/c
P2OUT = (0x00);
P2DIR = (0xFF);
// P2SEL = (BIT7|BIT6|BIT1|BIT0); // Enable XT1 and ACLK/SMCLK
//P2SEL = (BIT7|BIT6); // Enable XT1 only
P2SEL = (BIT1|BIT0); // Enable ACLK/SMCLK only
// P2SEL = (0x00); // Enable neither
// Port3 initialization
// P3.0 - n/c
// P3.1 - n/c
// P3.2 - n/c
// P3.3 - n/c
// P3.4 - n/c
// P3.5 - n/c
// P3.6 - n/c
// P3.7 - n/c
P3OUT = (0x00);
P3DIR = (0xFF);
P3SEL = (0x00);
// Port4 initialization
// P4.0 - n/c
// P4.1 - n/c
// P4.2 - n/c
// P4.3 - n/c
// P4.4 - n/c
// P4.5 - n/c
// P4.6 - n/c
// P4.7 - n/c
P4OUT = (0x00);
P4DIR = (0xFF);
P4SEL = (0x00);
}
void System_SetupACLK_VLO( void )
{ unsigned char byShadowBCSCTL3;
// Make sure XTS is clear
BCSCTL1 &= ~(XTS);
// Read the existing BCSCTL3 settings to the shadow
byShadowBCSCTL3 = BCSCTL3;
// Mask out the ACLK option bits
byShadowBCSCTL3 &= ~(LFXT1S1|LFXT1S0);
// Set the correct option for VLO
byShadowBCSCTL3 |= (LFXT1S_2);
// Update the register
BCSCTL3 = byShadowBCSCTL3;
}
void System_SetupTimerA3( void )
{
// Prepare the divisor
TACCR0 = (TICK_DIVISOR-1);
// Up Mode from ACLK
TACTL = (TASSEL_1|ID_0|MC_1|TACLR);
// Interrupt on CCR0
TACCTL0 = (CCIE);
}
void System_SetupWatchdogTimer( void )
{
// Configure the watchdog timer for 4 Hz interrupts from ACLK
WDTCTL = (WDT_ADLY_250);
// Defensively clear the WDT interrupt flag
IFG1 &= ~(WDTIFG);
// Enable the WDT
// IE1 |= (WDTIE);
}
#pragma vector=TIMERA0_VECTOR
__interrupt void TimerA_CCR0_ISR( void )
{
// Wake the processor
__low_power_mode_off_on_exit();
}
#pragma vector=WDT_VECTOR
__interrupt void WatchdogTimer_ISR( void )
{
// Wake the processor
__low_power_mode_off_on_exit();
}