110 lines
2.6 KiB
C
110 lines
2.6 KiB
C
#include"msp.h"
|
|
|
|
#define UNLOCK_CS CS->KEY = CS_KEY_VAL
|
|
#define LOCK_CS CS->KEY = 0
|
|
|
|
#define DISABLE_WATCHDOG() WDT_A->CTL= WDT_A_CTL_PW | WDT_A_CTL_HOLD
|
|
|
|
#define TIMER_PERIOD 20 // ms
|
|
#define TIMER_DIV (8)
|
|
#define TIMER_FCLK 3000000
|
|
#define TIMER_PERIOD_TICKS (((TIMER_FCLK / TIMER_DIV) * TIMER_PERIOD) / 1000)
|
|
|
|
//#define FULLRANGE
|
|
|
|
#ifdef FULLRANGE
|
|
#define DC_MIN 0.75
|
|
#define DC_MAX 2.25
|
|
#else
|
|
#define DC_MIN 1
|
|
#define DC_MAX 2
|
|
#endif
|
|
|
|
#define PERIOD TIMER_PERIOD_TICKS //20 ms
|
|
#define DUTY_MAX ((unsigned int)(TIMER_PERIOD_TICKS/TIMER_PERIOD)*(DC_MAX)) //2 ms
|
|
#define DUTY_MIN ((unsigned int)(TIMER_PERIOD_TICKS/TIMER_PERIOD)*(DC_MIN)) //1 ms
|
|
#define DUTY_RANGE (DUTY_MAX - DUTY_MIN)
|
|
|
|
|
|
#define ADC_MAX ((1 << 14) - 1)
|
|
#define ADC_MIN 0
|
|
#define ADC_RANGE ((ADC_MAX-ADC_MIN))
|
|
|
|
|
|
#define ADC_TO_T(v) (DUTY_MIN + ((v - ADC_MIN)*DUTY_RANGE)/ADC_RANGE)
|
|
|
|
|
|
void setup_pins(){
|
|
// J4 - P2.4
|
|
P2->DIR |= 0x10; //2.4
|
|
P2->SEL0 |= 0x10; //2.4 SELECT TA0 MODULE
|
|
P2->SEL1 &= ~0x10;//2.4 SELECT TA0 MODULE
|
|
|
|
// J3 - P4.0
|
|
P4->SEL0 |= 0x01; //4.0 SELECT ADC MODULE
|
|
P4->SEL1 |= 0x01; //4.0 SELECT ADC MODULE
|
|
}
|
|
|
|
void setup_clock(){
|
|
UNLOCK_CS;
|
|
|
|
CS->CTL0 |= CS_CTL0_DCORSEL_1; // 3 MHz
|
|
CS->CTL1 |= CS_CTL1_DIVS__8 | CS_CTL1_SELS__DCOCLK ; // SMCLOCK = DCLOCK/8
|
|
CS->CTL0 |= CS_CTL0_DCOEN; //Enable
|
|
|
|
LOCK_CS;
|
|
}
|
|
|
|
void setup_timer_a0(){
|
|
TIMER_A0->CCR[0] = PERIOD; //base period
|
|
|
|
TIMER_A0->CCR[1] = DUTY_MIN; //COMPARE to duty cycle
|
|
TIMER_A0->CCTL[1] = OUTMOD_7; //RESET/SET
|
|
|
|
TIMER_A0->EX0 = TAIDEX__1; // divide by 1
|
|
TIMER_A0->CTL = TASSEL__SMCLK | ID__1 | MC__UP;//DOWN; //SMCLK, /1, UP
|
|
}
|
|
|
|
void setup_adc(){
|
|
ADC14->CTL0 &= ~ADC14_CTL0_ENC; //ADC Disable
|
|
|
|
ADC14->CTL0 = ADC14_CTL0_ON; //ADC ON
|
|
ADC14->CTL0 |= ADC14_CTL0_SSEL__SMCLK; //USE SMCLK
|
|
|
|
ADC14->CTL0 |= ADC14_CTL0_CONSEQ_2; //ADC14 Repeat Channel Sampling
|
|
|
|
ADC14->CTL0 |= ADC14_CTL0_SHS_1; //USE TA0.1
|
|
|
|
ADC14->CTL1 = ADC14_CTL1_RES__14BIT; //14 bit, 16 clk conversion
|
|
|
|
ADC14->MCTL[0] = ADC14_MCTLN_VRSEL_0 | ADC14_MCTLN_INCH_13; // A13 ADC & V(R+) = AVCC, V(R-) = AVSS
|
|
ADC14->IER0 |= ADC14_IER0_IE0; //ADC Interrupt
|
|
|
|
ADC14->CTL0 |= ADC14_CTL0_ENC; //ADC Enable
|
|
}
|
|
|
|
|
|
|
|
void main(void){
|
|
DISABLE_WATCHDOG();
|
|
|
|
setup_pins();
|
|
setup_clock();
|
|
setup_timer_a0();
|
|
setup_adc();
|
|
|
|
SCB->SCR |= SCB_SCR_SLEEPONEXIT_Msk; // Enable sleep on exit from ISR
|
|
__DSB(); // Ensures SLEEPONEXIT takes effect immediately
|
|
__enable_irq(); // Enable global interrupt
|
|
|
|
NVIC_EnableIRQ(ADC14_IRQn); //ENABLE IRQ ADC14
|
|
|
|
__sleep(); //Sleep
|
|
}
|
|
|
|
|
|
void ADC14_IRQHandler(void) {
|
|
TIMER_A0->CCR[1] = ADC_TO_T(ADC14->MEM[0]);
|
|
}
|
|
|