Hello everyone, this is my first post here !
I am a newbie to CCS and CMSIS. I am student and I bought MSP432 launchpad for my research project to control a LED driver and also to record 8 analog channels and stream them to a computer. Where I got stuck is the streaming part via UART... I tried to dig through the MSPWare examples and inspire me from them but all I tried at the current time failed to function properly.
I explain more in details. For each of the 8 channels (A0-7) I want a loop to be :
- send on TXBUF the int 79 two times (it serves for verification of the received data on the link and as a scaling flag on the computer software interface as I want the UART out from the MSP432 to be an asynchronous stream)
- then send the channel number on TXBUF
- finally send the two bytes of ADC14MEM corresponding to the channel
I configured a DCO -> SMCLK @ 48 MHz to serve as source for the eUSCIa , and divided by UCABRS=100 to get a 480 Kbps baudrate .
Here is the CCS code :
#include "msp.h"
#include <stdint.h>
static uint8_t ch;
int main(void)
{
WDT_A->CTL = WDT_A_CTL_PW+WDT_A_CTL_HOLD; // Stop watchdog timer
CS->KEY = 0x695A; // unlock CS registers
CS->CTL0 = 0; // reset DCO settings
CS->CTL0 = CS_CTL0_DCORSEL_5; // select DCO 5 (48MHz)
CS->CTL1 = CS_CTL1_SELS__DCOCLK | CS_CTL1_SELM__DCOCLK; // ACLK = REFOCLK, SMCLK = MCLK = DCOCLK
CS->KEY = 0; // lock CS registers
// Configure GPIO
P5->SEL1 |= BIT5 | BIT4 | BIT3 | BIT2 | BIT1 | BIT0; // Enable A/D channel A0-A5
P5->SEL0 |= BIT5 | BIT4 | BIT3 | BIT2 | BIT1 | BIT0;
P4->SEL1 |= BIT7 | BIT6; // Enable A/D channel A6-A7
P4->SEL0 |= BIT7 | BIT6;
// ADC14 Configuration
ADC14->CTL0 = ADC14_CTL0_PDIV__32 | ADC14_CTL0_DIV_2 | ADC14_CTL0_ON | ADC14_CTL0_MSC | ADC14_CTL0_SHT0_0 | ADC14_CTL0_SHP | ADC14_CTL0_CONSEQ_3; // Turn on ADC14 750KHz, extend sampling time
ADC14->CTL1 = ADC14_CTL1_RES_3; // to avoid overflow of results
ADC14->MCTL[0] = ADC14_MCTLN_INCH_0; // ref+=AVcc, channel = A0
ADC14->MCTL[1] = ADC14_MCTLN_INCH_1; // ref+=AVcc, channel = A1
ADC14->MCTL[2] = ADC14_MCTLN_INCH_2; // ref+=AVcc, channel = A2
ADC14->MCTL[3] = ADC14_MCTLN_INCH_3; // ref+=AVcc, channel = A3.
ADC14->MCTL[4] = ADC14_MCTLN_INCH_4; // ref+=AVcc, channel = A4
ADC14->MCTL[5] = ADC14_MCTLN_INCH_5; // ref+=AVcc, channel = A5
ADC14->MCTL[6] = ADC14_MCTLN_INCH_6; // ref+=AVcc, channel = A6
ADC14->MCTL[7] = ADC14_MCTLN_INCH_7+ADC14_MCTLN_EOS; // +ADC14_MCTLN_VRSEL_14 ref+=AVcc, channel = A7, end seq.
SCB->SCR &= ~SCB_SCR_SLEEPONEXIT_Msk; // Wake up on exit from ISR
// Configure UART pins
P1->SEL0 |= BIT2 | BIT3; // set 2-UART pin as second function
// Configure UART
EUSCI_A0->CTLW0 |= EUSCI_A_CTLW0_SWRST; // Put eUSCI in reset
EUSCI_A0->CTLW0 |= EUSCI_A_CTLW0_SSEL__SMCLK; // Select SMCLK as eUSCIa clock source
// Baud Rate calculation
UCA0BR0 = 100; // 48000000/100 = 480000 bps
UCA0BR1 = 0;
EUSCI_A0->MCTLW = 0;
EUSCI_A0->CTLW0 &= ~EUSCI_A_CTLW0_SWRST; // Initialize eUSCI
EUSCI_A0->IE |= EUSCI_A_IE_RXIE; // Enable USCI_A0 RX interrupt
SCB->SCR &= ~SCB_SCR_SLEEPONEXIT_Msk; // Wake up on exit from ISR
ADC14->CTL0 |= ADC14_CTL0_ENC | ADC14_CTL0_SC; // Start conversion-software trigger
while(1)
{
for(ch=0;ch<8;ch++)
{
while(!(EUSCI_A0->IFG & EUSCI_A_IFG_TXIFG));
EUSCI_A0->TXBUF = 79; // Send marker-1 = 79 for stream scaling on computer side
while(!(EUSCI_A0->IFG & EUSCI_A_IFG_TXIFG));
EUSCI_A0->TXBUF = 79; // Send marker-2 = 79 for stream scaling on computer side
while(!(EUSCI_A0->IFG & EUSCI_A_IFG_TXIFG));
EUSCI_A0->TXBUF = ch+1; // Send channel number
while(!(EUSCI_A0->IFG & EUSCI_A_IFG_TXIFG));
EUSCI_A0->TXBUF = ADC14->MEM[ch]>>8; // Send MSByte from ADC14MEMch
while(!(EUSCI_A0->IFG & EUSCI_A_IFG_TXIFG));
EUSCI_A0->TXBUF = ADC14->MEM[ch]; // Send LSByte from ADC14MEMch
}
}
}
// UART interrupt service routine
void EUSCIA0_IRQHandler(void)
{
if (EUSCI_A0->IFG & EUSCI_A_IFG_RXIFG)
{
EUSCI_A0->IFG &=~ EUSCI_A_IFG_RXIFG; // Clear interrupt
}
}
On the other side I'm using python pySerial interface on Windows 8 and a time measure code for a serial read of 1 byte gives me very non-stable results (min value = 69us which is equivalent to 14Kbps and not 480 Kbps as expected from the baudrate). Python code :
while True :
start= time.clock()
self.ser.read(1)
print time.clock()-start
Thus I can't record the ADC values at 480/8 Kbps (or any fixed sampling rate) .... Does it come from my CCS code or could it be a problem coming from python pySerial module ?
Thank you in advance !