Forum: Mikrocontroller und Digitale Elektronik EFM23TG840F32 UART initialise


von Octavian T. (tunea)


Angehängte Dateien:

Lesenswert?

Hello everybody.

I have a microcontroller EFM32TG840F32 and a UART-USB adapter.
I want to connect the UART-USB to a Pc and receive a byte from the 
terminal program from PC (like 5A="Z"in ASCII). When this byte it is 
read from the UART1 by the microcontroller, he should send back a 
character sequence - "Energy Micro". Pd0=Tx and PD1=Rx.

I have used IAR as IDE and I used the example USART from their website. 
But it looks like the initialisation of the UART it is not done and I 
receive no data. I tried also to send back what I receive in the 
receivebuffer and still does not work.

can you give me a hint to what I have done wrong?
does anyone programmed the USART1 or USART2 from this microcontroller? I 
never used it before. I attached also the code and I copy paste also my 
main functions.

///main.c

#include <string.h>
#include "efm32.h"
#include "efm32_chip.h"
#include "efm32_cmu.h"
#include "uart.h"
#include "usart.h"


/* Buffers */
char transmitBuffer[] = "Energy Micro";
#define Zet 0x5A
#define            BUFFERSIZE    (sizeof(transmitBuffer) / sizeof(char))
char receiveBuffer[];

/*********************************************************************** 
*******
 * @brief enables high frequency crystal oscillator (HFXO),
 * Sets HFCLK domain to use HFXO as source
 ************************************************************************ 
*****/
void switchToHFXO(void)
{
  CMU_TypeDef *cmu = CMU;

  /* Turning on HFXO to increase frequency accuracy. */
  /* Waiting until oscillator is stable */
  cmu->OSCENCMD = CMU_OSCENCMD_HFXOEN;

  while (!(cmu->STATUS && CMU_STATUS_HFXORDY)) ;

  /* Switching the CPU clock source to HFXO */
  cmu->CMD = CMU_CMD_HFCLKSEL_HFXO;

  /* Turning off the high frequency RC Oscillator (HFRCO) */
  /* GENERATL WARNING! Make sure not to disable the current
   * source of the HFCLK. */
  cmu->OSCENCMD = CMU_OSCENCMD_HFRCODIS;
}



/*********************************************************************** 
*******
 * @brief initializing uart settings
 *
 ************************************************************************ 
*****/
void init(void)
{
  /* Using HFXO to have max frequency accuracy */
  switchToHFXO();

 // CMU_ClockEnable(cmuClock_GPIO, true);


   /* Setup UART */
  UART_setupUart(USART1_NUM, GPIO_POS1);

    /* Enabling clock to USART 1 and 2*/
  CMU_ClockEnable(cmuClock_USART1, true);
}


/*********************************************************************** 
*******
 * @brief  Main function
 * Main is called from _program_start, see assembly startup file
 ************************************************************************ 
*****/
int main(void)
{
  /* Initialize chip */
  CHIP_Init();

  /* Initalizing */
  init();

/* Clearing the receive buffer */
memset(receiveBuffer, '\0', 1);

  while(receiveBuffer[0]!=Zet)

  {
    /* Transmitting data */
  /* Transmission is polled */
    UART1_receiveBuffer(receiveBuffer,1);
    USART1_sendBuffer(receiveBuffer, 1);
  }
      USART1_sendBuffer(transmitBuffer, BUFFERSIZE);

  /* Done! */
  while (1) ;
}


/*this is my UART.C file*/

#include "efm32.h"
#include "uart.h"
#include "efm32_gpio.h"
#include "uart_project.h"
#include "usart.h"
#include "efm32_cmu.h"

#include <string.h>

/* Buffer pointers and indexes */
char* txBuffer;
char* rxBuffer;
int txBufferSize;
int rxBufferSize;
volatile int txBufferIndex;
volatile int rxBufferIndex;



/*********************************************************************** 
***//**
 * @brief Setup a USART to be used in asynchronous (UART) mode
 * @param usartNumber is the number of the USART to use (e.g. 1 for 
USART1)
 * @param location is the IO location to use
 ************************************************************************ 
*****/
void UART_setupUart(uint8_t uartNumber, uint8_t location)
{
  USART_TypeDef* uart = USART1;


  /* Configure USART as uart - 8-N-1 */
  uart->FRAME &= ~(
    _USART_FRAME_DATABITS_MASK |
    _USART_FRAME_PARITY_MASK |
    _USART_FRAME_STOPBITS_MASK);
  uart->FRAME |= (
    USART_FRAME_DATABITS_EIGHT |
    USART_FRAME_PARITY_NONE |
    USART_FRAME_STOPBITS_ONE
    );


  /* Setting baudrate */
  uart->CLKDIV = 256 * ((UART_PERCLK_FREQUENCY / (16 * UART_BAUDRATE)) - 
1);


  /* Enable RX/TX */
  uart->CMD = USART_CMD_RXEN | USART_CMD_TXEN;

   /* Enable RX and TX pins and set location */
  uart->ROUTE = USART_ROUTE_RXPEN | USART_ROUTE_TXPEN | (1 << 8);

  /* Clear RX/TX buffers */
  uart->CMD = USART_CMD_CLEARRX | USART_CMD_CLEARTX;


  /* Use default location 0: TX - Pin D0, RX - Pin D1 */
  /* To avoid false start, configure output as high */
 GPIO_PinModeSet(gpioPortD, 0, gpioModePushPull, 0);

  /* Define input, no filtering */
 GPIO_PinModeSet(gpioPortD, 1, gpioModeInput, 0);

 GPIO_PinModeSet(gpioPortD, 1, gpioModeInputPull, 0);


}


/*********************************************************************** 
***//**
 * @brief Receiving data from USART1
 * @param receiveBuffer is pointing to where data is to be stored.
 * @param bytesToReceive is the number of bytes to receive
 ************************************************************************ 
*****/
void UART1_receiveBuffer(char* receiveBuffer, int bytesToReceive)
{
  USART_TypeDef *uart = USART1;
  int           ii;

  /* Receiving data */
  for (ii = 0; ii < bytesToReceive;  ii++)
  {
    /* Waiting for the usart to be ready */
 while (!(uart->STATUS & USART_STATUS_RXDATAV)) ;

    /* Writing next byte to USART */
    *receiveBuffer = uart->RXDATA;
    receiveBuffer++;
  }
}

/*********************************************************************** 
*******
 * @brief sends data using USART1
 * @param txBuffer points to data to transmit
 * @param bytesToSend bytes will be sent
 ************************************************************************ 
*****/
void USART1_sendBuffer(char* txBuffer, int bytesToSend)
{
  USART_TypeDef *uart = USART1;
  int           ii;

  /* Sending the data */
  for (ii = 0; ii < bytesToSend;  ii++)
  {
    /* Waiting for the usart to be ready */
  while (!(uart->STATUS & USART_STATUS_TXBL)) ;

    if (txBuffer != 0)
    {
      /* Writing next byte to USART */
      uart->TXDATA = *txBuffer;
      txBuffer++;
    }
    else
    {
      uart->TXDATA = 0;
    }
  }

  /*Waiting for transmission of last byte */
  while (!(uart->STATUS & USART_STATUS_TXC)) ;
}


thank you.

von Ben j. (scarab)


Lesenswert?

i dont looked through the whole code but common errors on 
EnergyMicro-Controllers are:

- you dont enabled the peripheral clock (-> all peripherals are 
disabled, you cant even set a GPIO )
- your GPIO-PinModes doesn't match the ROUTE of your UART
- your using the wrong registers to read out the buffer (there i 
register that returns the byte for the UART but doesnt delete this byte 
from the buffer)

maybe u should try to use energyAware Designer to generate the 
Initialisation.

Also the EM support is very fast:
http://support.energymicro.com/anonymous_requests/new

von Octavian T. (tunea)


Lesenswert?

Hello.

thank you for the answear. I enabled all clocks - GPIO clock and UART 
clock.
The GPIO pin initialising I took it from the Energy Aware designer which 
generates the code for something you need on this board.
When it comes to registers I am not sure about my code but I do not know 
exactly where to look.

in the datasheet it is written that for transmission I must set 
TxEN(from USARTn_CMD register), disable TxDIS (from USARTn_CMD 
register), load frame - write to  USARtn_TxDATA

for the receive I use RxDATAV to validate data.

I already wrote them also but they say I did something wrong with the 
interrupts, but I use no interrupts or maybe something in the UART 
initialising is not ok.
Thanks

von Jim M. (turboj)


Lesenswert?

You need to enable clocks before accessing perpherials in your init() 
function:
1
  /* Enabling clock to USART 1*/
2
  CMU_ClockEnable(cmuClock_USART1, true);
3
4
  /* Setup UART */
5
  UART_setupUart(USART1_NUM, GPIO_POS1);

von Octavian T. (tunea)


Angehängte Dateien:

Lesenswert?

I have solved the promblem. the board Tiny gecko had a problem with this 
UART. I tried it on another board - Starter Kit EFM32G890F128 and it 
worked.

I attach the final code. this code sends back the bytes it receives from 
the PC. I tested it with Terminal by br@y.

Have a nice day everybody.

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.