cancel
Showing results for 
Search instead for 
Did you mean: 

STM32F407 Discovery - Problem with UART1

rafal2
Associate II
Posted on January 17, 2015 at 13:27

I have just started my adventures with STM32f407 Discovery board. I'm using latest stable release of CoIDE and using up to date toolchain/libraries.

I managed to write the following code in order to use USART1 from the board

int main(void)
{
GPIO_InitTypeDef GPIO_InitStructure; // Definicja struktury do inicjalizacji PINOW
USART_InitTypeDef USART_InitStructure;
// Initialize pins as alternating function
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9 | GPIO_Pin_10;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz;
GPIO_Init(GPIOA, &GPIO_InitStructure);
GPIO_PinAFConfig(GPIOA, GPIO_PinSource9, GPIO_AF_USART1);
GPIO_PinAFConfig(GPIOA, GPIO_PinSource10, GPIO_AF_USART1);
// Modify USART_InitStructure for non -default values , e.g.
// USART_InitStructure.USART_BaudRate = 38400;
USART_InitStructure.USART_BaudRate = 9600;
USART_InitStructure.USART_WordLength = USART_WordLength_8b;
USART_InitStructure.USART_StopBits = USART_StopBits_1;
USART_InitStructure.USART_Parity = USART_Parity_No;
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
USART_InitStructure.USART_Mode = USART_Mode_Tx|USART_Mode_Rx;
USART_Init(USART1 ,&USART_InitStructure);
USART_Cmd(USART1 , ENABLE);
while(1)
{
while (USART_GetFlagStatus(USART1 , USART_FLAG_TXE) == RESET);
USART1 ->DR = (uint16_t)(45 & 0x01FF);
Delay(0x3FFFFF);
}
}

0690X00000605ECQAY.png And as you can see on the attached picture I'm receiving incorrect data. Bascially if I change value sent the characters on the console are the same. I have defined settings for clock configuration and confirmed it is working fine

#if !defined (HSE_VALUE)
#define HSE_VALUE ((uint32_t)8000000) /*!< Value of the External oscillator in Hz */
#endif /* HSE_VALUE */
/************************* PLL Parameters *************************************/
/* PLL_VCO = (HSE_VALUE or HSI_VALUE / PLL_M) * PLL_N */
#define PLL_M 8
#define PLL_N 336
/* SYSCLK = PLL_VCO / PLL_P */
#define PLL_P 2
/* USB OTG FS, SDIO and RNG Clock = PLL_VCO / PLLQ */
#define PLL_Q 7
/******************************************************************************/

Now in order to find the root cause I have tried to configure USART3 and this one works out of the box.

int main( void) 
{
GPIO_InitTypeDef GPIO_InitStructure;
USART_InitTypeDef USART_InitStructure;
/* Enable GPIO clock */
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOC, ENABLE);
/* Enable UART clock */
RCC_APB1PeriphClockCmd(RCC_APB1Periph_USART3, ENABLE);
/* Connect PXx to USARTx_Tx*/
GPIO_PinAFConfig(GPIOC, GPIO_PinSource10, GPIO_AF_USART3);
/* Connect PXx to USARTx_Rx*/
GPIO_PinAFConfig(GPIOC, GPIO_PinSource11, GPIO_AF_USART3);
/* Configure USART Tx as alternate function */
GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOC, &GPIO_InitStructure);
/* Configure USART Rx as alternate function */
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_11;
GPIO_Init(GPIOC, &GPIO_InitStructure);
USART_InitStructure.USART_BaudRate = 9600;
USART_InitStructure.USART_WordLength = USART_WordLength_8b;
USART_InitStructure.USART_StopBits = USART_StopBits_1;
USART_InitStructure.USART_Parity = USART_Parity_No;
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;
/* USART configuration */
USART_Init(USART3, &USART_InitStructure);
/* Enable USART */
USART_Cmd(USART3, ENABLE);
SysTick_Config(SystemCoreClock / 1000);
while(1)
{
for (int var = 45; var < 128; var++)
{
USART_SendData(USART3, var);
Delay_SysTick(500); // 1 sek
}
}
}

Can anyone point me to some possible root causes ? I have already tried multiple baud rates on PC terminal / different USB<>RS232 (mostly FT232RL chips ) and slowly running out of any ideas. Regards Rafal
8 REPLIES 8
Posted on January 17, 2015 at 14:11

Can anyone point me to some possible root causes ?

Well there's that 4.7uF capacitor on PA9

Tips, buy me a coffee, or three.. PayPal Venmo Up vote any posts that you find helpful, it shows what's working..
rafal2
Associate II
Posted on January 17, 2015 at 14:28

Thanks Clive for pointout. I have found your previous reply now under [DEAD LINK /public/STe2ecommunities/mcu/Lists/STM32Discovery/Flat.aspx?RootFolder=/public/STe2ecommunities/mcu/Lists/STM32Discovery/Help%20with%20GPIO%20on%20STM32F4%20discovery&FolderCTID=0x01200200770978C69A1141439FE559EB459D75800084C20D8867EAD444A5987D47BE638E0F&currentviews=956]here

However is this somehow document for beginners ?

Posted on January 17, 2015 at 14:54

However is this somehow document for beginners ?

Well there is the User Manual for the board, which has both a schematic, and a list of usable pins.
Tips, buy me a coffee, or three.. PayPal Venmo Up vote any posts that you find helpful, it shows what's working..
rafal2
Associate II
Posted on January 17, 2015 at 15:19

If I may just ask on this one. Looking at the table from user manual (from beginner perspective ) I have Main function / Alternate function and board function. And in this particular example PA9 (USART1 TX) has board function of ''VBUS'' and ''GREEN LED''.

So would this be correct If I would say I cannot use alternate function if there is a board function assigned to it ?

Posted on January 17, 2015 at 16:25

Unfortunately ''beginner'' is a bit vague, I'm assuming you're not three, and bring some life skills to the party. Do you have experience with electronics, microprocessors, software, try to provide some context.

You'd want to focus on the ''Free I/O'' pins, the other pins are connected to other things, and so you'd need to review the circuit, attached components, and decide if the current configuration would interfere with other uses, or if you need to remove the components.

The STM32F4-DISCO has quite a lot of external circuitry, for access to more pins/functions consider a more basic breakout board configuration,.

Tips, buy me a coffee, or three.. PayPal Venmo Up vote any posts that you find helpful, it shows what's working..
world04
Associate II
Posted on January 18, 2015 at 23:31

At first, the clock source is wrong initilized - your init code enables the clock source for COM3 instead COM1 you handles in your code.

Secount, take care about the bus where the com ports attached. This could a different one - so watch into the manual of the 407.

You should inititialize the structure before you fill  up them. I give you an example of my UART3 code that uses IRQ and Showes you how this works.

/* Includes ------------------------------------------------------------------*/

#include ''stm32f4xx.h''

#include <stm32f4xx_usart.h>

#include <stdio.h>

#include <string.h>

#include <uart4.h>

/*******************************************************************************

* Function Name  : UART4_Configuration

* Description    : Configure UART4

* Input          : PC10 = TX

* Output         : PC11 = RX

* Return         : None

* Attention     : UART connected to APB1; GPIOC connected to AHB1

*                : The library does'nt handles te UART and USART different

*  DD4DA

*******************************************************************************/

void UART4Init ( uint32_t baudrate )

{

 GPIO_InitTypeDef   GPIO_InitStructure;

 USART_InitTypeDef  USART_InitStructure;

 NVIC_InitTypeDef   NVIC_InitStructure;              // this is used to configure the NVIC (nested vector interrupt controller)

 RCC_APB1PeriphClockCmd ( RCC_APB1Periph_UART4, ENABLE );    // UART4 is connect to APB1

 RCC_AHB1PeriphClockCmd ( RCC_AHB1Periph_GPIOC, ENABLE );       // UART4 used Port-C, Pin10 as TXD,Pin11 as RXD

 GPIO_DeInit ( GPIOC );                       // RESET CMD TO GPIOC      - ob das ne gute idee ist

 //  UART4_TX -> PC10 , UART4_RX -> PC11

 GPIO_StructInit ( &GPIO_InitStructure );

 GPIO_InitStructure.GPIO_Pin   = GPIO_Pin_10 | GPIO_Pin_11;   // GPIO Pin10 (TxD) und Pin11(RxD)

 GPIO_InitStructure.GPIO_Mode  = GPIO_Mode_AF;          // GPIO in Alternate Function mode

 GPIO_InitStructure.GPIO_Speed  = GPIO_Speed_25MHz;       // SlewRate

 GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;         // PushPull

 GPIO_Init ( GPIOC, &GPIO_InitStructure );            // GPIOC

 // Connect UART4 pins to GPIOC

 GPIO_PinAFConfig ( GPIOC, GPIO_PinSource10, GPIO_AF_UART4 );  // Alternate Function von GPIOC, Pin 10 an UART4 TX mappen

 GPIO_PinAFConfig ( GPIOC, GPIO_PinSource11, GPIO_AF_UART4 );  // Alternate Function von GPIOC, Pin 11 an UART4 RX mappen

 

 USART_StructInit ( &USART_InitStructure );

 USART_InitStructure.USART_BaudRate   = baudrate;

 USART_InitStructure.USART_WordLength  = USART_WordLength_8b;

 USART_InitStructure.USART_StopBits   = USART_StopBits_1;

 USART_InitStructure.USART_Parity    = USART_Parity_No;

 USART_InitStructure.USART_HardwareFlowControl  = USART_HardwareFlowControl_None;

 USART_InitStructure.USART_Mode     = USART_Mode_Rx | USART_Mode_Tx;

 

 USART_Init ( UART4, &USART_InitStructure );

 NVIC_InitStructure.NVIC_IRQChannel = UART4_IRQn;       // we want to configure the UART4 interrupts

 NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0; // this sets the priority group of the USART1 interrupts

 NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;       // this sets the subpriority inside the group

 NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;       // the UART4 interrupts are globally enabled

 

 NVIC_Init ( &NVIC_InitStructure );

 USART_ITConfig ( UART4, USART_IT_RXNE, ENABLE );        // RX-Data not empty IRQ

 USART_Cmd ( UART4, ENABLE );

}

#define RXQLEN  32     // max RX-Pufferlänge

int   Uart4RxCnt;      // Anzahl aktueller zeichen im RX-Puffer

char   Uart4RxQ[RXQLEN];   // RX-Puffer

void UART4_IRQHandler ( void )

{

 while ( USART_GetITStatus ( UART4, USART_IT_RXNE ) != RESET )

  {

   Uart4RxQ[Uart4RxCnt++] = USART_ReceiveData ( UART4 );

  }

}

void UART4PutData ( uint16_t  x )

{

 USART_SendData ( USART3, x );

 while ( !USART_GetFlagStatus ( UART4, USART_FLAG_TXE ) );

}

void UART4PutChar ( void *c )

{

 USART_SendData ( UART4, * ( uint16_t * ) c );

 while ( !USART_GetFlagStatus ( UART4, USART_FLAG_TXE ) );

}

void UART4PutString ( const char *str )

{

 do

  {

   UART4PutChar ( ( void * ) str ) ;

  }

 while ( * ( uint8_t * ) str++ != '\0' );

}

Posted on January 19, 2015 at 00:13

Some inconsistent use of USART3 vs UART4, and back testing of TXE rather than front testing. You want to test if a register is EMPTY before you put something in it.

Tips, buy me a coffee, or three.. PayPal Venmo Up vote any posts that you find helpful, it shows what's working..
childresss
Associate II
Posted on January 19, 2015 at 04:15

Suggestion to help newbie get started...

download and use STM's free CubeMX tool for setting up clocks and mapping I/O pins. It then generates all the startup code based on your choices.