/* * sci.c * * Created on: Apr 7, 2016 * Author: de360684 SAILESH PANDEY */ #include "sci.h" #define CPU_FREQ 100E6 #define LSPCLK_FREQ CPU_FREQ/4 #define SCI_FREQ 100E3 #define SCI_PRD (LSPCLK_FREQ/(SCI_FREQ*8))-1 #define BAUDSTEP 100 //unsigned char Data_Receive; //unsigned char SCIFLAG; unsigned short sdataA[8]; // Send data for SCI-A unsigned short rdataA[8]; // Received data for SCI-A unsigned short sdataB[8]; // Send data for SCI-B unsigned short rdataB[8]; // Received data for SCI-B unsigned short sdataC[8]; // Send data for SCI-C unsigned short rdataC[8]; // Received data for SCI-C unsigned short *rdata_pointA; // Used for checking the received data unsigned short *rdata_pointB; // Used for checking the received data unsigned short *rdata_pointC; // Used for checking the received data unsigned short LoopCount; //Uint16 xmitCount; unsigned short ReceivedCount; unsigned short ErrorCount; unsigned short SendChar; unsigned short ReceivedAChar; // scia received character unsigned short ReceivedBChar; // scib received character unsigned short BRRVal; unsigned short Buff[10] = {0x55, 0xAA, 0xF0, 0x0F, 0x00, 0xFF, 0xF5, 0x5F, 0xA5, 0x5A}; void scia_fifo_init(); void scib_fifo_init(); void scic_fifo_init(); void scic_xmit(int a); void scib_xmit(int a); void Gpio_SciA_init(void); void Gpio_SciB_init(void); void Gpio_SciC_init(void); __interrupt void sciaRxFifoIsr(void); __interrupt void sciaTxFifoIsr(void); __interrupt void scibRxFifoIsr(void); __interrupt void scibTxFifoIsr(void); __interrupt void scicRxFifoIsr(void); __interrupt void scicTxFifoIsr(void); void InitSci(void) { unsigned char i; /* Configuration of gpio as SCI TX and RX */ Gpio_SciA_init(); Gpio_SciB_init(); Gpio_SciC_init(); EALLOW; // This is needed to write to EALLOW protected registers /* SCI-A Interrupts */ //PieVectTable.SCIRXINTA = &sciaRxFifoIsr; //PieVectTable.SCITXINTA = &sciaTxFifoIsr; /* SCI-B Interrupts */ PieVectTable.SCIRXINTB = &scibRxFifoIsr; //PieVectTable.SCITXINTB = &scibTxFifoIsr; /* SCI-C Interrupts */ //PieVectTable.SCIRXINTC = &scicRxFifoIsr; //PieVectTable.SCITXINTC = &scicTxFifoIsr; EDIS; scia_fifo_init(); // Init SCI-A scib_fifo_init(); // Init SCI-B scic_fifo_init(); // Init SCI-C LoopCount = 0; ErrorCount = 0; // Enable interrupts PieCtrlRegs.PIEIER9.all = 0x0001; // Enable all SCIA RXINT interrupt IER |= 0x0100; // enable PIEIER9, and INT9 EINT; // SCIB has a known baud rate. SCIA will autobaud to match //ScibRegs.SCIHBAUD = (BRRVal >> 8); ScibRegs.SCILBAUD = (30); ScicRegs.SCILBAUD = (30); ScibRegs.SCICTL1.bit.SWRESET = 0; ScibRegs.SCICTL1.bit.SWRESET = 1; ScicRegs.SCICTL1.bit.SWRESET = 0; ScicRegs.SCICTL1.bit.SWRESET = 1; SendChar = 23; while(1) { scib_xmit(SendChar); scic_xmit(SendChar); } /* // Start with BRR = 1, work through each baud rate setting // incrementing BRR by BAUDSTEP for (BRRVal = 0x0010; BRRVal < (Uint32)0x40; BRRVal+=BAUDSTEP) { // SCIB has a known baud rate. SCIA will autobaud to match ScibRegs.SCIHBAUD = (BRRVal >> 8); ScibRegs.SCILBAUD = (BRRVal); // Initiate an autobaud lock with scia. Check // returned character against baud lock character 'A' scib_AutobaudLock(); while(ScibRegs.SCIRXST.bit.RXRDY != 1) { } ReceivedBChar = 0; ReceivedBChar = ScibRegs.SCIRXBUF.bit.RXDT; if(ReceivedBChar != 'A') { error(0); } // Send/echoback characters // 55 AA F0 0F 00 FF F5 5F A5 5A for(i= 0; i<=9; i++) { SendChar = Buff[i]; scib_xmit(SendChar); // Initiate interrupts and xmit data in isr // Wait to get the character back and check // against the sent character. while(ScibRegs.SCIRXST.bit.RXRDY != 1) { __asm(" NOP"); } ReceivedBChar = 0; ReceivedBChar = ScibRegs.SCIRXBUF.bit.RXDT; if(ReceivedBChar != SendChar) error(1); } } // Repeat for next BRR setting */ // Stop here, no more for(;;) { __asm(" NOP"); } } void error() { __asm(" ESTOP0"); // Test failed!! Stop! for (;;); } __interrupt void scibRxFifoIsr(void) { // Insert ISR Code here PieCtrlRegs.PIEACK.all = PIEACK_GROUP9; // If autobaud detected, we must clear CDC if(ScibRegs.SCIFFCT.bit.ABD == 1) { ScibRegs.SCIFFCT.bit.ABDCLR = 1; ScibRegs.SCIFFCT.bit.CDC = 0; // Check received character - should be 'A' ReceivedAChar = 0; ReceivedAChar = ScibRegs.SCIRXBUF.all; if(ReceivedAChar != 'A') { error(2); } else scic_xmit(ReceivedAChar); } // This was not autobaud detect else { // Check received character against sendchar ReceivedAChar = 0; ReceivedAChar = ScibRegs.SCIRXBUF.all; if(ReceivedAChar != SendChar) { error(3); } else scib_xmit(ReceivedAChar); } ScibRegs.SCIFFRX.bit.RXFFINTCLR = 1; // clear Receive interrupt flag ReceivedCount++; } void scia_fifo_init() { // Note: Clocks were turned on to the SCIA peripheral // in the InitSysCtrl() function // Reset FIFO's SciaRegs.SCIFFTX.all=0x8000; SciaRegs.SCICCR.all =0x0007; // 1 stop bit, No loopback // No parity,8 char bits, // async mode, idle-line protocol SciaRegs.SCICTL1.all =0x0003; // enable TX, RX, internal SCICLK, // Disable RX ERR, SLEEP, TXWAKE SciaRegs.SCICTL2.all =0x0003; SciaRegs.SCICTL2.bit.RXBKINTENA =1; SciaRegs.SCICTL1.all =0x0023; // Relinquish SCI from Reset } void scib_fifo_init() { // Note: Clocks were turned on to the SCIA peripheral // in the InitSysCtrl() function // Reset FIFO's ScibRegs.SCIFFTX.all=0x8000; ScibRegs.SCICCR.all =0x0007; // 1 stop bit, No loopback // No parity,8 char bits, // async mode, idle-line protocol ScibRegs.SCICTL1.all =0x0003; // enable TX, RX, internal SCICLK, // Disable RX ERR, SLEEP, TXWAKE ScibRegs.SCICTL2.all =0x0003; ScibRegs.SCICTL2.bit.RXBKINTENA =1; ScibRegs.SCICTL1.all =0x0023; // Relinquish SCI from Reset } void scic_fifo_init() { // Note: Clocks were turned on to the SCIA peripheral // in the InitSysCtrl() function // Reset FIFO's ScicRegs.SCIFFTX.all=0x8000; ScicRegs.SCICCR.all =0x0007; // 1 stop bit, No loopback // No parity,8 char bits, // async mode, idle-line protocol ScicRegs.SCICTL1.all =0x0003; // enable TX, RX, internal SCICLK, // Disable RX ERR, SLEEP, TXWAKE ScicRegs.SCICTL2.all =0x0003; ScicRegs.SCICTL2.bit.RXBKINTENA =1; ScicRegs.SCICTL1.all =0x0023; // Relinquish SCI from Reset } void Gpio_SciA_init(void) { GpioCtrlRegs.GPBPUD.bit.GPIO35 = 0; // Enable pull-up for GPIO29 (SCITXDA) GpioCtrlRegs.GPAPUD.bit.GPIO28 = 0; // Enable pull-up for GPIO28 (SCIRXDA) GpioCtrlRegs.GPAQSEL2.bit.GPIO28 = 3; // Asynch input GPIO28 (SCIRXDA) GpioCtrlRegs.GPBMUX1.bit.GPIO35 = 1; // Configure GPIO29 for SCITXDA operation GpioCtrlRegs.GPAMUX2.bit.GPIO28 = 1; // Configure GPIO28 for SCIRXDA operation } void Gpio_SciB_init(void) { GpioCtrlRegs.GPAPUD.bit.GPIO22 = 0; // Enable pull-up for GPIO22 (SCITXDA) GpioCtrlRegs.GPAPUD.bit.GPIO23 = 0; // Enable pull-up for GPIO23 (SCIRXDA) GpioCtrlRegs.GPAQSEL2.bit.GPIO23 = 3; // Asynch input GPIO23 (SCIRXDA) GpioCtrlRegs.GPAMUX2.bit.GPIO22 = 3; // Configure GPIO29 for SCITXDA operation GpioCtrlRegs.GPAMUX2.bit.GPIO23 = 3; // Configure GPIO28 for SCIRXDA operation } void Gpio_SciC_init(void) { GpioCtrlRegs.GPBPUD.bit.GPIO62 = 0; // Enable pull-up for GPIO62 (SCIRXDA) GpioCtrlRegs.GPBPUD.bit.GPIO63 = 0; // Enable pull-up for GPIO63 (SCITXDA) GpioCtrlRegs.GPBQSEL2.bit.GPIO62 = 3; // Asynch input GPIO62 (SCIRXDA) GpioCtrlRegs.GPBMUX2.bit.GPIO62 = 1; // Configure GPIO62 for SCITXDA operation GpioCtrlRegs.GPBMUX2.bit.GPIO63 = 1; // Configure GPIO63 for SCIRXDA operation } // Transmit a character from the SCI-A' void scib_xmit(int a) { ScibRegs.SCITXBUF=a; } // Transmit a character from the SCI-B' void scic_xmit(int a) { ScicRegs.SCITXBUF=a; } void scib_AutobaudLock() { ScibRegs.SCICTL1.bit.SWRESET = 0; ScibRegs.SCICTL1.bit.SWRESET = 1; // Must prime baud register with >= 1 ScibRegs.SCIHBAUD = 0; ScibRegs.SCILBAUD = 1; // Prepare for autobaud detection // Make sure the ABD bit is clear by writing a 1 to ABDCLR // Set the CDC bit to enable autobaud detection ScibRegs.SCIFFCT.bit.ABDCLR = 1; ScibRegs.SCIFFCT.bit.CDC = 1; // Wait until we correctly read an // 'A' or 'a' and lock // // As long as Autobaud calibration is enabled (CDC = 1), // SCI-B (host) will continue transmitting 'A'. This will // continue until interrupted by the SCI-A RX ISR, where // SCI-A RXBUF receives 'A', autobaud-locks (ABDCLR=1 // CDC=0),and returns an 'A' back to the host. Then control // is returned to this loop and the loop is exited. // // NOTE: ABD will become set sometime between // scib_xmit and the DELAY_US loop, and // the SCI-A RX ISR will be triggered. // Upon returning and reaching the if-statement, // ABD will have been cleared again by the ISR. while(ScibRegs.SCIFFCT.bit.CDC== 1) { // Note the lower the baud rate the longer // this delay has to be to allow the other end // to echo back a character (about 4 characters long) // Make this really long since we are going through all // the baud rates. DELAY_US(28000L); if(ScibRegs.SCIFFCT.bit.CDC == 1) scic_xmit('A'); // host transmits 'A' } return; }