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.

MSP430F5659: Implement UART using DMA to receive and Transfer data of 256 bytes using UART

Part Number: MSP430F5659
Other Parts Discussed in Thread: MSP430F6736

Hi all,

I'm working on a project where I need to implement UART communication using DMA on a MSP430F5659. Specifically, I need to reliably receive and transfer data packets of 256 bytes via UART. I understand that DMA can significantly offload the CPU and improve efficiency for such tasks.

Could anyone provide guidance or share some sample code on how to set up UART communication with DMA for handling 256-byte data transfers efficiently? I'm particularly interested in how to configure the DMA channels, UART peripheral, and any necessary interrupt handling for seamless operation.

Any insights, or code snippets would be greatly appreciated!

Thanks in advance.

  • I think TI doesn't provide an Example which does exactly this. I suggest you start with the Tx side, since that's a bit simpler. For that, I (still) suggest the Example msp430f665x_dma_02.c, over here:

    https://dev.ti.com/tirex/explore/node?node=A__AOA7HJs5vP6JteXGeExmkQ__msp430ware__IOGqZri__LATEST

    As I mentioned, this uses a rather unusual triggering mechanism (using a timer). The usual method would be to replace:

    >   DMACTL0 = DMA0TSEL_1;                     // 0-CCR2IFG

    with

    >   DMACTL0 = DMA0TSEL_21;                    // UCA1TXIFG trigger per SLAS700E Table 9-13

    where I got "21" from the DMA trigger table in the data sheet. I suggest also changing

    >  DMA0CTL = DMADT_4 | DMASRCINCR_3 | DMASBDB | DMAEN;// Rpt, inc src, enable

    to 

    >  DMA0CTL = DMADT_4 | DMASRCINCR_3 | DMASBDB | DMAEN | DMALEVEL;// Rpt, inc src, enable, level trigger

    to avoid an arcane first-byte thing. The transmission will start immediately since this sets DMAEN=1. You can get rid of the timer code.

    If you run this program it will send "Hello" repeatedly (handy for debugging). To do it only once, change DMADT_4 -> DMADT_0.

  • Hi Baseer,

    Are you saying that you need to receive UART data, transfer it to memory using DMA, then use DMA again to transfer out via UART again?

    I am able to provide a snippet of code that I wrote to receive UART data and transfer it to memory. I do not have code available to set up the second DMA to transfer from memory to UART TX, but the snippet can help you get to a starting point, and Bruce's input above will also be helpful. The code snippet that I will paste is written for the MSP430F6736, so you will need to check the pins and registers, but the flow should be similar as they are the same device family. 

    The snippet simply receives UART data at 9600 baud, and fills a buffer with the received data. When the received data fills the buffer, it begins to overwrite the beginning of the buffer. Please see below:

    Fullscreen
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    #include <msp430.h>
    #include <stdint.h>
    #define NUM_OF_BYTES (10) // Update this with the number of bytes to receive over
    // UART and store in the buffer
    // UART RX Values
    unsigned int DMA_DST[NUM_OF_BYTES] = {0x00};
    int main(void)
    {
    WDTCTL = WDTPW | WDTHOLD; // Stop WDT
    // Setup P1.4 UCA1RXD, P1.5 UCA1TXD
    P1SEL |= BIT4 | BIT5; // Set P1.4, P1.5 to non-IO
    P1DIR |= BIT4 | BIT5; // Enable UCA1RXD, UCA1TXD
    // Setup eUSCI_A1
    UCA1CTLW0 |= UCSWRST; // **Put state machine in reset**
    UCA1CTLW0 |= UCSSEL__SMCLK; // SMCLK
    UCA1BRW_L = 6; // 1MHz 9600 (see User's Guide)
    XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX

    I will add: something that held me up for a while was that the DMA will not trigger while the corresponding interrupt is enabled. So in that example, I originally had the UART RX interrupt enabled, and couldn't get the DMA to trigger. Make sure that you keep the interrupt disabled, and if you need the second DMA channel, ensure that the TX interrupt is also disabled.

  • Hi Dylan and Bruce,

    Thanks for the help let me follow your guidelines and will get back if I face any issues. Thanks again.

**Attention** This is a public forum