This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

TIVA uDMA Ping-Pong UART: Skipping byte (error in transmission)

Hi TI E2E Community,

 I’m trying to set-up the Tiva’s uDMA to do a Ping-Pong transfer into UART0 TX Data register, I need to transfer data at high speed, hence I have configured UART0 to run at 921,600 bps. While looking at the output in the serial terminal, I’m seeing that from time to time the UART/uDMA skips a bit, shifting the test sequence being used.

Any idea why?

I have changed the baud rate to 115200 trying to identify the problem, but the same situation persists.

I would really appreciate the help of the TI community!

Thanks,

Daniel

/*
 * main.c
 *
 *  Created on: Feb 2, 2016
 *      Author: daniel
 */

#include <stdint.h>
#include <stdbool.h>
#include <stdlib.h>
#include <stdio.h>
#include "inc/hw_memmap.h"
#include "inc/hw_types.h"
#include "inc/hw_ints.h"
#include "inc/hw_uart.h"
#include "inc/hw_adc.h"
#include "driverlib/debug.h"
#include "driverlib/sysctl.h"
#include "driverlib/adc.h"
#include "driverlib/gpio.h"
#include "driverlib/rom.h"
#include "driverlib/interrupt.h"
#include "driverlib/pin_map.h"
#include "driverlib/uart.h"
#include "driverlib/udma.h"


#define TARGET_IS_BLIZZARD_RB1
#define NumOfChannels 16
#define AdcTransferSize 8

#define J_LIMIT (NumOfChannels/2)-1

// uDMA control table aligned to 1024-byte boundary
#pragma DATA_ALIGN(DMAParameters, 1024)
uint8_t DMAParameters[1024];



void initAdc(void);
void initUartTransfer(void);
void initAdcTransfer(void);
void dmaErrorHandler(void);
void uartIntHandler(void);
void adcIntHandler(void);
void processData(void);


//Fill and process pointers
volatile short *fillAdc;
volatile short *processAdc;

volatile short *transmitUart;
volatile short *fillUart;

//= {17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32}
//= {0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15}

short AdcPingBuf[NumOfChannels];
short AdcPongBuf[NumOfChannels];

short UartTxPing[NumOfChannels] = {
		0x3210,
		0x7654,
		0xBA98,
		0xFEDC,
		0x3210,
		0x7654,
		0xBA98,
		0xFEDC,
		0x3210,
		0x7654,
		0xBA98,
		0xFEDC,
		0x3210,
		0x7654,
		0xBA98,
		0xFEDC
};

short UartTxPong[NumOfChannels] = {
		0x3210,
		0x7654,
		0xBA98,
		0xFEDC,
		0x3210,
		0x7654,
		0xBA98,
		0xFEDC,
		0x3210,
		0x7654,
		0xBA98,
		0xFEDC,
		0x3210,
		0x7654,
		0xBA98,
		0xFEDC
};

/*
 * {
		0x0000,
		0x1111,
		0x2222,
		0x3333,
		0x4444,
		0x5555,
		0x6666,
		0x7777,
		0x8888,
		0x9999,
		0xAAAA,
		0xBBBB,
		0xCCCC,
		0xDDDD,
		0xEEEE,
		0xFFFF
};
 */

int adcPingCount = 0;
int adcPongCount = 0;

int uartPingCount = 0;
int uartPongCount = 0;

int adcInterruptCounter = 0;
int uartInterruptCounter = 0;

int edmaErrorCount = 0;

int *adc0Fifo = (void *) (ADC0_BASE + ADC_O_SSFIFO0);
int *adc1Fifo = (void *) (ADC1_BASE + ADC_O_SSFIFO0);



//DEBUG
volatile short dataSample;

int main(void)
{

	//	uint16_t ui32_ADC0_ss_3; //Channel 0
	//	uint16_t ui32_ADC0_ss_2[4]; //Channel 1,2,3,4
	//	uint16_t ui32_ADC0_ss_1[4]; //Channel 5,6,7,8
	//	uint16_t ui32_ADC0_ss_0[8]; //Channel 9,10,11
	//
	//	uint16_t ui32_ADC1_ss_3; //Channel 12
	//	uint16_t ui32_ADC1_ss_2[4]; //Channel 13,14,15,16
	//	uint16_t ui32_ADC1_ss_1[4]; //Channel 17,18,19,20
	//	uint16_t ui32_ADC1_ss_0[8]; //Channel 21,22,23


	/*
	 * Config clock: Choose main Osc, drive the PLL with a 16 Mhz crystal. The PLL has a frequency of 400 MHz.
	 * It is initially divided by two, so 200 MHz (unless there is a DIV 400). The system clock is being divided then by 4.
	 * Then 200/4 = 50 MHz. The system clock is configured to run at 50 MHz.
	 */
	SysCtlClockSet(SYSCTL_SYSDIV_4|SYSCTL_USE_PLL|SYSCTL_OSC_MAIN|SYSCTL_XTAL_16MHZ);

	//Enable ADC0 and ADC1
	SysCtlPeripheralEnable(SYSCTL_PERIPH_ADC0);
	SysCtlPeripheralEnable(SYSCTL_PERIPH_ADC1);

	// GPIO setup for UART
	SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOC);
	SysCtlPeripheralSleepEnable(SYSCTL_PERIPH_UART0);
	GPIOPinConfigure(GPIO_PC4_U1RX);
	GPIOPinConfigure(GPIO_PC5_U1TX);
	GPIOPinTypeUART(GPIO_PORTC_BASE, GPIO_PIN_4 | GPIO_PIN_5);

	//GPIO setup for ADc
	SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOE);
	SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOD);
	SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOB);
	SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOK);

	GPIOPinTypeADC(GPIO_PORTE_BASE, GPIO_PIN_0 | GPIO_PIN_1| GPIO_PIN_2| GPIO_PIN_3);
	GPIOPinTypeADC(GPIO_PORTD_BASE, GPIO_PIN_7 | GPIO_PIN_6| GPIO_PIN_5| GPIO_PIN_4| GPIO_PIN_3| GPIO_PIN_2);
	GPIOPinTypeADC(GPIO_PORTB_BASE, GPIO_PIN_4 | GPIO_PIN_5);
	GPIOPinTypeADC(GPIO_PORTK_BASE, GPIO_PIN_0 | GPIO_PIN_1| GPIO_PIN_2| GPIO_PIN_3);

	// Enable uDMA
	SysCtlPeripheralEnable(SYSCTL_PERIPH_UDMA);
	SysCtlPeripheralSleepEnable(SYSCTL_PERIPH_UDMA);
	IntEnable(INT_UDMAERR);

	uDMAControlBaseSet(DMAParameters);

	uDMAEnable();
	//initAdc();
	initUartTransfer();
	//initAdcTransfer();

	fillUart = UartTxPong;
	transmitUart = UartTxPing;

	IntMasterEnable();

	while(1){

	}
}


void initAdc(void){

	/* ADCClockConfigSet Shared between ADC devices, only one required. Using PLL. Docs say that PLL/25 will be used.
	 * Use PIOSC at 16 Mhz, at 125 kS/s.
	 */
	ADCClockConfigSet(ADC0_BASE,ADC_CLOCK_SRC_PIOSC|ADC_CLOCK_RATE_EIGHTH,1);

	/*
	 *Hardware over-sampling to take the 125 kS/s to ~2 kS/s.
	 * 125/64 = 1.95 kS/s ~= 2 kS/s
	 */
	ADCHardwareOversampleConfigure(ADC0_BASE, 64);
	ADCHardwareOversampleConfigure(ADC1_BASE, 64);


	//Sequencer COnfigure
	ADCSequenceConfigure(ADC0_BASE, 0, ADC_TRIGGER_ALWAYS,0);
	//ADCSequenceConfigure(ADC0_BASE, 1, ADC_TRIGGER_ALWAYS,1);


	ADCSequenceConfigure(ADC1_BASE, 0, ADC_TRIGGER_ALWAYS,0);
	//ADCSequenceConfigure(ADC1_BASE, 1, ADC_TRIGGER_ALWAYS,1);

	//ADC Step Configure

	//ADC0
	//Sample Sequencer 0, FIFO size = 8, Channel 0-7, Arbitration size must be 8.
	ADCSequenceStepConfigure(ADC0_BASE,0,0,ADC_CTL_CH0);
	ADCSequenceStepConfigure(ADC0_BASE,0,1,ADC_CTL_CH1);
	ADCSequenceStepConfigure(ADC0_BASE,0,2,ADC_CTL_CH2);
	ADCSequenceStepConfigure(ADC0_BASE,0,3,ADC_CTL_CH3);
	ADCSequenceStepConfigure(ADC0_BASE,0,4,ADC_CTL_CH4);
	ADCSequenceStepConfigure(ADC0_BASE,0,5,ADC_CTL_CH5);
	ADCSequenceStepConfigure(ADC0_BASE,0,6,ADC_CTL_CH6);
	ADCSequenceStepConfigure(ADC0_BASE,0,7,ADC_CTL_CH7|ADC_CTL_IE|ADC_CTL_END);

	//Sample Sequencer 1, FIFO size = 4, Channel 8-11, Arbitration size must be 4.
	/*
	ADCSequenceStepConfigure(ADC0_BASE,1,0,ADC_CTL_CH8);
	ADCSequenceStepConfigure(ADC0_BASE,1,1,ADC_CTL_CH9);
	ADCSequenceStepConfigure(ADC0_BASE,1,2,ADC_CTL_CH10);
	ADCSequenceStepConfigure(ADC0_BASE,1,3,ADC_CTL_CH11|ADC_CTL_END|ADC_CTL_IE);
	 */


	//ADC1
	//Sample Sequencer 0, FIFO size = 8, Channel 10-13 & 16-19, Arbitration size must be 8.
	ADCSequenceStepConfigure(ADC1_BASE,0,0,ADC_CTL_CH10);
	ADCSequenceStepConfigure(ADC1_BASE,0,1,ADC_CTL_CH11);
	ADCSequenceStepConfigure(ADC1_BASE,0,2,ADC_CTL_CH12);
	ADCSequenceStepConfigure(ADC1_BASE,0,3,ADC_CTL_CH13);
	ADCSequenceStepConfigure(ADC1_BASE,0,4,ADC_CTL_CH16);
	ADCSequenceStepConfigure(ADC1_BASE,0,5,ADC_CTL_CH17);
	ADCSequenceStepConfigure(ADC1_BASE,0,6,ADC_CTL_CH18);
	ADCSequenceStepConfigure(ADC1_BASE,0,7,ADC_CTL_CH19|ADC_CTL_IE|ADC_CTL_END);

	//Sample Sequencer 1, FIFO size = 4, Channel 20-23, Arbitration size must be 4.
	/*
	ADCSequenceStepConfigure(ADC1_BASE,1,0,ADC_CTL_CH20);
	ADCSequenceStepConfigure(ADC1_BASE,1,1,ADC_CTL_CH21);
	ADCSequenceStepConfigure(ADC1_BASE,1,2,ADC_CTL_CH22);
	ADCSequenceStepConfigure(ADC1_BASE,1,3,ADC_CTL_CH23|ADC_CTL_END|ADC_CTL_IE);
	 */

	//Enable sequencer
	ADCSequenceEnable(ADC0_BASE, 0);
	//ADCSequenceEnable(ADC0_BASE, 1);


	ADCSequenceEnable(ADC1_BASE, 0);
	//ADCSequenceEnable(ADC1_BASE, 1);
}

// Initialize UART uDMA transfer
void initUartTransfer(void){

	//Clear UART TX buffers
	/*int i = 0;
	for(i = 0; i < NumOfChannels; i++){
		UartTxPing[i] = 0;
		UartTxPong[i] = 0;
	}*/
	//	char cmd[2];
	//	*(cmd) = 'O';
	//	*(cmd + 1) = 'K';
	//	UartTxPing[0] = ((cmd[1])<<8)|(cmd[0]);
	//UartTxPing[0] = (short) *cmd;

	// Enable UART1 and make sure it can run while the CPU sleeps
	SysCtlPeripheralEnable(SYSCTL_PERIPH_UART1);
	SysCtlPeripheralSleepEnable(SYSCTL_PERIPH_UART1);

	// Configure and enable the UART with DMA
	UARTConfigSetExpClk(UART1_BASE, SysCtlClockGet(), 921600,
			UART_CONFIG_WLEN_8 | UART_CONFIG_STOP_ONE |
			UART_CONFIG_PAR_NONE);

	//FIFO's are depth 16, 1/2 trigger means 8 FIFO's are free. This can be adjusted, make sure
	//to change arbitration size in uDMA config.
	UARTFIFOEnable(UART1_BASE);
	UARTFIFOLevelSet(UART1_BASE, UART_FIFO_TX4_8, UART_FIFO_TX4_8);

	UARTEnable(UART1_BASE);
	UARTDMAEnable(UART1_BASE, UART_DMA_TX);


	IntEnable(INT_UART1);

	// Tx channel setup for ping and pong
	uDMAChannelAttributeDisable(UDMA_CHANNEL_UART1TX,
			UDMA_ATTR_ALTSELECT | UDMA_ATTR_USEBURST |
			UDMA_ATTR_HIGH_PRIORITY |
			UDMA_ATTR_REQMASK);

	uDMAChannelControlSet(UDMA_CHANNEL_UART1TX | UDMA_PRI_SELECT,
			UDMA_SIZE_8 | UDMA_SRC_INC_8 | UDMA_DST_INC_NONE |
			UDMA_ARB_4);

	uDMAChannelControlSet(UDMA_CHANNEL_UART1TX | UDMA_ALT_SELECT,
			UDMA_SIZE_8 | UDMA_SRC_INC_8 | UDMA_DST_INC_NONE |
			UDMA_ARB_4);

	uDMAChannelAttributeEnable(UDMA_CHANNEL_UART1TX,UDMA_ATTR_HIGH_PRIORITY|UDMA_ATTR_USEBURST);



	uDMAChannelTransferSet(UDMA_CHANNEL_UART1TX | UDMA_PRI_SELECT,
			UDMA_MODE_PINGPONG,UartTxPing,(void *)(UART1_BASE + UART_O_DR), NumOfChannels*2);

	uDMAChannelTransferSet(UDMA_CHANNEL_UART1TX | UDMA_ALT_SELECT,
			UDMA_MODE_PINGPONG,UartTxPong,(void *)(UART1_BASE + UART_O_DR), NumOfChannels*2);



	// Enable TX channel
	uDMAChannelEnable(UDMA_CHANNEL_UART1TX);
}

void initAdcTransfer(void){

	//Clear ADC buffers

	int i = 0;
	for(i = 0; i < NumOfChannels; i++){
		AdcPingBuf[i] = 0;
		AdcPongBuf[i] = 0;
	}




	//Enable DMA signaling.
	ADCSequenceDMAEnable(ADC0_BASE,0);
	// ADCSequenceDMAEnable(ADC0_BASE,1);
	ADCSequenceDMAEnable(ADC1_BASE,0);
	// ADCSequenceDMAEnable(ADC1_BASE,1);

	//Enable DMA interruptions, remember this get intercepted by DMA.
	IntEnable(INT_ADC0SS0);
	//IntEnable(INT_ADC0SS1);
	IntEnable(INT_ADC1SS0);
	//IntEnable(INT_ADC1SS1);

	ADCIntEnableEx(ADC0_BASE,ADC_INT_DMA_SS0);
	ADCIntEnableEx(ADC1_BASE,ADC_INT_DMA_SS0);

	//Select secondary mapping for channel 24
	uDMAChannelAssign(UDMA_CH24_ADC1_0);


	// DMA ADC ping/pong configuration
	uDMAChannelAttributeDisable(UDMA_CHANNEL_ADC0,
			UDMA_ATTR_ALTSELECT | UDMA_ATTR_USEBURST |
			UDMA_ATTR_HIGH_PRIORITY |
			UDMA_ATTR_REQMASK);

	uDMAChannelAttributeDisable(UDMA_SEC_CHANNEL_ADC10,
			UDMA_ATTR_ALTSELECT | UDMA_ATTR_USEBURST |
			UDMA_ATTR_HIGH_PRIORITY |
			UDMA_ATTR_REQMASK);

	uDMAChannelAttributeEnable(UDMA_CHANNEL_ADC0,UDMA_ATTR_USEBURST);
	uDMAChannelAttributeEnable(UDMA_SEC_CHANNEL_ADC10,UDMA_ATTR_USEBURST);


	//Configure Primary and Alternate for ADC0
	uDMAChannelControlSet(UDMA_CHANNEL_ADC0 | UDMA_PRI_SELECT,
			UDMA_SIZE_16 | UDMA_SRC_INC_NONE | UDMA_DST_INC_16 |
			UDMA_ARB_8);

	uDMAChannelControlSet(UDMA_CHANNEL_ADC0 | UDMA_ALT_SELECT,
			UDMA_SIZE_16 | UDMA_SRC_INC_NONE | UDMA_DST_INC_16 |
			UDMA_ARB_8);



	uDMAChannelTransferSet(UDMA_CHANNEL_ADC0 | UDMA_PRI_SELECT,
			UDMA_MODE_PINGPONG,(void *)(ADC0_BASE + ADC_O_SSFIFO0),AdcPingBuf, AdcTransferSize);

	uDMAChannelTransferSet(UDMA_CHANNEL_ADC0 | UDMA_ALT_SELECT,
			UDMA_MODE_PINGPONG,(void *)(ADC0_BASE + ADC_O_SSFIFO0),AdcPongBuf, AdcTransferSize);



	//Configure Primary and Alternate for ADC1
	uDMAChannelControlSet(UDMA_SEC_CHANNEL_ADC10 | UDMA_PRI_SELECT,
			UDMA_SIZE_16 | UDMA_SRC_INC_NONE | UDMA_DST_INC_16 |
			UDMA_ARB_8);

	uDMAChannelControlSet(UDMA_SEC_CHANNEL_ADC10 | UDMA_ALT_SELECT,
			UDMA_SIZE_16 | UDMA_SRC_INC_NONE | UDMA_DST_INC_16 |
			UDMA_ARB_8);



	uDMAChannelTransferSet(UDMA_SEC_CHANNEL_ADC10 | UDMA_PRI_SELECT,
			UDMA_MODE_PINGPONG,(void *)(ADC1_BASE + ADC_O_SSFIFO0),&(AdcPingBuf[8]), AdcTransferSize);

	uDMAChannelTransferSet(UDMA_SEC_CHANNEL_ADC10 | UDMA_ALT_SELECT,
			UDMA_MODE_PINGPONG,(void *)(ADC1_BASE + ADC_O_SSFIFO0),&(AdcPongBuf[8]), AdcTransferSize);



	// Enable ADC channels
	uDMAChannelEnable(UDMA_CHANNEL_ADC0);
	uDMAChannelEnable(UDMA_SEC_CHANNEL_ADC10);
}


// uDMA error handler
void dmaErrorHandler(void){

	uint32_t ui32Status;

	ui32Status = uDMAErrorStatusGet();

	if(ui32Status)
	{
		uDMAErrorStatusClear();
		edmaErrorCount++;
	}
}

// UART interrupt handler. Called on completion of uDMA transfer
void uartIntHandler(void){

	uint32_t ui32Status;
	uint32_t ui32Mode;

	ui32Status = UARTIntStatus(UART1_BASE, 1);

	UARTIntClear(UART1_BASE, ui32Status);

	//UART PING
	//Determine if TX primary structure is done. If it is, reset the structure to original parameters.
	ui32Mode = uDMAChannelModeGet(UDMA_CHANNEL_UART1TX | UDMA_PRI_SELECT);

	if(ui32Mode == UDMA_MODE_STOP)
	{
		uartPingCount++;
		uDMAChannelTransferSet(UDMA_CHANNEL_UART1TX | UDMA_PRI_SELECT,
				UDMA_MODE_PINGPONG,UartTxPing,(void *)(UART1_BASE + UART_O_DR), NumOfChannels*2);

		transmitUart = UartTxPing;
		fillUart = UartTxPong;
	}


	//UART PONG
	//Determine if TX alternate structure is done, if it is, reset the structure to original parameters.
	ui32Mode = uDMAChannelModeGet(UDMA_CHANNEL_UART1TX | UDMA_ALT_SELECT);

	if(ui32Mode == UDMA_MODE_STOP)
	{
		uartPongCount++;

		uDMAChannelTransferSet(UDMA_CHANNEL_UART1TX | UDMA_ALT_SELECT,
				UDMA_MODE_PINGPONG,UartTxPong,(void *)(UART1_BASE + UART_O_DR), NumOfChannels*2);

		transmitUart = UartTxPong;
		fillUart = UartTxPing;
	}

	uartInterruptCounter++;

}

void adcIntHandler(void){


	volatile uint32_t ui32StatusADC0;
	volatile uint32_t ui32StatusADC1;
	volatile uint32_t ui32Mode;

	//Determine which module initiated the interrupt and clear it.
	ui32StatusADC0 = ADCIntStatus(ADC0_BASE,0,true);
	ui32StatusADC1 = ADCIntStatus(ADC1_BASE,0,true);

	if(ui32StatusADC0 == ADC_INT_SS0){
		ADCIntClear(ADC0_BASE,0);
	}

	if(ui32StatusADC1 == ADC_INT_SS0){
		ADCIntClear(ADC1_BASE,0);
	}

	/////////////////////////////////////////ADC0 Param Refill///////////////////////////////////

	//PING
	//Determine if ADC primary structure is done. If it is, reset the structure to original parameters.
	ui32Mode = uDMAChannelModeGet(UDMA_CHANNEL_ADC0 | UDMA_PRI_SELECT);

	if(ui32Mode == UDMA_MODE_STOP)
	{
		adcPingCount++;
		uDMAChannelTransferSet(UDMA_CHANNEL_ADC0 | UDMA_PRI_SELECT,
				UDMA_MODE_PINGPONG,(void *)(ADC0_BASE + ADC_O_SSFIFO0),AdcPingBuf, AdcTransferSize);
	}

	//PONG
	//Determine if ADC alternate structure is done, if it is, reset the structure to original parameters.
	ui32Mode = uDMAChannelModeGet(UDMA_CHANNEL_ADC0 | UDMA_ALT_SELECT);

	if(ui32Mode == UDMA_MODE_STOP)
	{
		adcPongCount++;

		uDMAChannelTransferSet(UDMA_CHANNEL_ADC0 | UDMA_ALT_SELECT,
				UDMA_MODE_PINGPONG,(void *)(ADC0_BASE + ADC_O_SSFIFO0),AdcPongBuf, AdcTransferSize);

		uDMAChannelEnable(UDMA_CHANNEL_ADC0);
	}


	//////////////////////////////////////ADC1 Param Refill//////////////////////////////////////

	//PING
	//Determine if ADC primary structure is done. If it is, reset the structure to original parameters.
	ui32Mode = uDMAChannelModeGet(UDMA_SEC_CHANNEL_ADC10 | UDMA_PRI_SELECT);

	if(ui32Mode == UDMA_MODE_STOP)
	{
		adcPingCount++;
		uDMAChannelTransferSet(UDMA_SEC_CHANNEL_ADC10 | UDMA_PRI_SELECT,
				UDMA_MODE_PINGPONG,(void *)(ADC1_BASE + ADC_O_SSFIFO0),&(AdcPingBuf[8]), AdcTransferSize);


	}

	//PONG
	//Determine if ADC alternate structure is done, if it is, reset the structure to original parameters.
	ui32Mode = uDMAChannelModeGet(UDMA_SEC_CHANNEL_ADC10 | UDMA_ALT_SELECT);

	if(ui32Mode == UDMA_MODE_STOP)
	{
		adcPongCount++;

		uDMAChannelTransferSet(UDMA_SEC_CHANNEL_ADC10 | UDMA_ALT_SELECT,
				UDMA_MODE_PINGPONG,(void *)(ADC1_BASE + ADC_O_SSFIFO0),&(AdcPongBuf[8]), AdcTransferSize);

		uDMAChannelEnable(UDMA_SEC_CHANNEL_ADC10);
	}

	//If ping has been executed in both ADC0 & ADC1. Reset ping counter, swap fill process.
	if(adcPingCount >= 2){
		adcPingCount = 0;
		processAdc = AdcPingBuf;
		fillAdc = AdcPongBuf;
		processData();
	}

	if(adcPongCount >= 2){
		adcPongCount = 0;
		processAdc = AdcPongBuf;
		fillAdc = AdcPingBuf;
		processData();
	}

	adcInterruptCounter++;

}

void processData(void){

	short onlyTwelveBitMask = 0xFFF;

	short shiftToId = 0x1000;

	int i = 0;
	for(i = 0; i < NumOfChannels; i++){
		fillUart[i] = 0;
		fillUart[i] = processAdc[i];
		fillUart[i] &= onlyTwelveBitMask;
		fillUart[i]  |= (i * shiftToId);
	}

	//dataSample = fillUart[0];


}

  • Sounds like a baud rate mismatch, a marginal match can drift so that the start bit is detected in the wrong place.

    Also check your stop bit configuration. It's nice if both sides can transmit more than they require on receipt but it's not usual to be capable of setting that up. What you don't want is the receiver to be expecting two stop bits when the transmitter sends fewer. That will possibly work until you get two unfortunate characters close together.

    I assume you are using high speed 485/422 but even then noise could be an issue.

    Robert