Tip / Sign in to post questions, reply, level up, and achieve exciting badges. Know more

cross mob
Ahlan
Level 1
Level 1
First reply posted First question asked Welcome!
I am trying to program the XMC4500 Relax board without using Dave or the XMC libraries. Therefore the core and clock setup is my own code. I have programmed USIC module 1 channel 0 as ASC and can transmit. However, the baudrate is out by a factor of 5. With PDIV=316, PCTQ=0 and DCTQ=15, I expected a baud are of 19'200 yet the baudrate of the output is 3840 ie as if fPeriph were 24 MHz (fOsi) rather than 120 MHz (fSys). However, my understanding is that, if undivided, fPeriph should be fSys so why then is it still at its boot value? I measured the time taken to execute a set of instructions and saw that this reduced as I ramped up the PLL speed reaching the expected factor of 5 when I reached 120 MHz. This convinces me that fCpu is 120 MHZ. I note that Systick does not change and remains at 24 MHz. This too was unexpected, so perhaps this gives a clue as to whatI am doing wrong. Has anyone any suggestions or ideas why my serial IO has the wrong baudrate? Best regards, Ahlan
0 Likes
1 Solution
LinglingG_46
Moderator
Moderator
Moderator
500 solutions authored 1000 replies posted 10 questions asked

First of all:

Please make sure you set the peripheral clock in the right way and get the value you want. You can check the below codes to get the peripheral  clock 72Mhz. ASC clock comes from system clock.  You can use the sys tick time interrupt to test the cpu clock.

 

#define CLOCK_CCUCLK_ENABLED 1U
#define CLOCK_CCUCLK_DIV 1U
#define CLOCK_CPUCLK_DIV 1U
#define CLOCK_FOFI_CALIBRATION_MODE XMC_SCU_CLOCK_FOFI_CALIBRATION_MODE_FACTORY
#define CLOCK_OSCHP_ENABLED 1U
#define CLOCK_OSCHP_MODE XMC_SCU_CLOCK_OSCHP_MODE_OSC
#define CLOCK_PERICLK_DIV 1U
#define CLOCK_SYSPLL_ENABLED 1U
#define CLOCK_SYSPLL_SEL XMC_SCU_CLOCK_SYSPLLCLKSRC_OSCHP
#define CLOCK_SYSPLL_MODE XMC_SCU_CLOCK_SYSPLL_MODE_NORMAL
#define CLOCK_SYSPLL_PDIV 1U
#define CLOCK_SYSPLL_NDIV 24U
#define CLOCK_SYSPLL_KDIV 1U
#define CLOCK_RTCCLK_SEL XMC_SCU_HIB_RTCCLKSRC_OSI
#define CLOCK_STDBYCLK_SEL XMC_SCU_HIB_STDBYCLKSRC_OSI
#define CLOCK_SYSCLK_SEL XMC_SCU_CLOCK_SYSCLKSRC_PLL
#define CLOCK_SYSCLK_DIV 4U

void SystemCoreClockSetup(void)
{
  XMC_SCU_CLOCK_CONFIG_t clock_config =
  {
  #if defined(CLOCK_SYSPLL_ENABLED)
    .syspll_config.n_div = CLOCK_SYSPLL_NDIV,
    .syspll_config.p_div = CLOCK_SYSPLL_PDIV,
    .syspll_config.k_div = CLOCK_SYSPLL_KDIV,
    .syspll_config.clksrc=CLOCK_SYSPLL_SEL,
    .syspll_config.mode = CLOCK_SYSPLL_MODE,
  #else
    .syspll_config.mode = XMC_SCU_CLOCK_SYSPLL_MODE_DISABLED,
  #endif
  #if defined(CLOCK_OSCHP_ENABLED)
    .enable_oschp = true,
  #endif
  #if defined(CLOCK_OSCLP_ENABLED)
    .enable_osculp = true,
  #endif
    .calibration_mode = CLOCK_FOFI_CALIBRATION_MODE,
    .fstdby_clksrc=CLOCK_STDBYCLK_SEL,
    .fsys_clksrc=CLOCK_SYSCLK_SEL,
    .fsys_clkdiv = CLOCK_SYSCLK_DIV,
    .fcpu_clkdiv = CLOCK_CPUCLK_DIV,
  #if defined(CLOCK_CCUCLK_ENABLED)
    .fccu_clkdiv = CLOCK_CCUCLK_DIV,
  #endif
    .fperipheral_clkdiv = CLOCK_PERICLK_DIV
  };
 
 #if defined(CLOCK_EXTCLK_ENABLED)
  /* External output source clock */
  XMC_SCU_CLOCK_SetExternalOutputClockSource(CLOCK_EXTCLK_SEL);
  /* External clock divider setting */
  XMC_SCU_CLOCK_SetExternalOutputClockDivider(CLOCK_EXTCLK_DIV);
 #endif
   
  XMC_SCU_CLOCK_Init(&clock_config);
 
  /* RTC source clock */
  XMC_SCU_HIB_SetRtcClockSource(CLOCK_RTCCLK_SEL);
 
 #if defined(CLOCK_USBCLK_ENABLED)
   /* USB/SDMMC source clock */
   XMC_SCU_CLOCK_SetUsbClockSource(CLOCK_USBCLK_SEL);
   /* USB/SDMMC divider setting */
   XMC_SCU_CLOCK_SetUsbClockDivider(CLOCK_USBCLK_DIV);
 #endif
 
 #if defined(CLOCK_USBPLL_ENABLED)
  XMC_SCU_CLOCK_EnableUsbPll();
  XMC_SCU_CLOCK_StartUsbPll(CLOCK_USBPLL_PDIV, CLOCK_USBPLL_NDIV);
 #endif  
 #if defined(CLOCK_ECATCLK_ENABLED)
  /* ECAT source clock */
  XMC_SCU_CLOCK_SetECATClockSource(CLOCK_ECATCLK_SEL);
  /* ECAT divider setting */
  XMC_SCU_CLOCK_SetECATClockDivider(CLOCK_ECATCLK_DIV);
 #endif
 
 #if defined(CLOCK_WDTCLK_ENABLED)
  /* WDT source clock */
  XMC_SCU_CLOCK_SetWdtClockSource(CLOCK_WDTCLK_SEL);
  /* WDT divider setting */
  XMC_SCU_CLOCK_SetWdtClockDivider(CLOCK_WDTCLK_DIV);
 #endif
 
 #if defined(CLOCK_EBUCLK_ENABLED)
  /* EBU divider setting */
  XMC_SCU_CLOCK_SetEbuClockDivider(CLOCK_EBUCLK_DIV);
 #endif 
  #if defined(CLOCK_USBCLK_ENABLED)
  XMC_SCU_CLOCK_EnableClock(XMC_SCU_CLOCK_USB);
 #endif
 #if defined(CLOCK_SDCLK_ENABLED)
  XMC_SCU_CLOCK_EnableClock(XMC_SCU_CLOCK_MMC);
 #endif
 #if defined(CLOCK_ETHCLK_ENABLED)
  XMC_SCU_CLOCK_EnableClock(XMC_SCU_CLOCK_ETH);
 #endif
 #if defined(CLOCK_EBUCLK_ENABLED)
  XMC_SCU_CLOCK_EnableClock(XMC_SCU_CLOCK_EBU);
 #endif
 #if defined(CLOCK_CCUCLK_ENABLED)
  XMC_SCU_CLOCK_EnableClock(XMC_SCU_CLOCK_CCU);
 #endif
 #if defined(CLOCK_WDTCLK_ENABLED)
  XMC_SCU_CLOCK_EnableClock(XMC_SCU_CLOCK_WDT);
 #endif
}

 

 

 

The following steps show how to get the 19200 bps baud rate.

For example:

The peripheral clock is 72Mhz.

1: Set the sample point:

Sample_point=8

 

 

__STATIC_INLINE void XMC_UART_CH_SetSamplePoint(XMC_USIC_CH_t *const channel, const uint32_t sample_point)
{
  channel->PCR_ASCMode = (uint32_t)((channel->PCR_ASCMode & (uint32_t)(~USIC_CH_PCR_ASCMode_SP_Msk)) |
                                    (sample_point << USIC_CH_PCR_ASCMode_SP_Pos));
}

 

 

2: SetFractionalDivider:(Fractional mode selected and step set the value 1017)

 

 

__STATIC_INLINE void XMC_USIC_CH_SetFractionalDivider(XMC_USIC_CH_t *const channel, const XMC_USIC_CH_BRG_CLOCK_DIVIDER_MODE_t mode, const uint16_t step)
{
  channel->FDR = mode | step;
}

 

 

Mode=32768

Step=1017

  channel->FDR = mode | step;

LinglingG_46_0-1704783410829.png

 

3: The the ASC module get the input clock fpin

Fpin= Fperi/(1023/step)=72000000/(1023/1017)=72000000/1.0058997 =71577712

 

 

void XMC_USIC_CH_SetBaudrateDivider(XMC_USIC_CH_t *const channel, 
                                    XMC_USIC_CH_BRG_CLOCK_SOURCE_t clksel,
                                    bool pppen,
                                    uint32_t pdiv,
                                    XMC_USIC_CH_BRG_CTQSEL_t ctqsel,
                                    uint32_t pctq,
                                    uint32_t dctq)
{
    uint32_t regval = channel->BRG;
    regval &= (uint32_t)~(USIC_CH_BRG_CLKSEL_Msk | USIC_CH_BRG_PPPEN_Msk | USIC_CH_BRG_PDIV_Msk | USIC_CH_BRG_CTQSEL_Msk | USIC_CH_BRG_PCTQ_Msk | USIC_CH_BRG_DCTQ_Msk);
    regval |= clksel | (pppen ? USIC_CH_BRG_PPPEN_Msk : 0) | (pdiv << USIC_CH_BRG_PDIV_Pos) | ctqsel | (pctq << USIC_CH_BRG_PCTQ_Pos) | (dctq << USIC_CH_BRG_DCTQ_Pos);
    channel->BRG = regval;
}

 

 

 

LinglingG_46_1-1704783410833.png

 

4: Then we can refer the below screen to get the baud rate:

FASC=71577712/(233*16) =19200bps

LinglingG_46_2-1704783410842.png

 

It is recommended that you can use the component or the lib to achieve the function first, then depending the successful project to do the developing.

Last but not least, we can refer to the XMC4500 reference manual  here .

Hope it can be helpful for you to have a deep understanding of the baud rate generating.

 

 

 

 

View solution in original post

0 Likes
3 Replies
LinglingG_46
Moderator
Moderator
Moderator
500 solutions authored 1000 replies posted 10 questions asked

First of all:

Please make sure you set the peripheral clock in the right way and get the value you want. You can check the below codes to get the peripheral  clock 72Mhz. ASC clock comes from system clock.  You can use the sys tick time interrupt to test the cpu clock.

 

#define CLOCK_CCUCLK_ENABLED 1U
#define CLOCK_CCUCLK_DIV 1U
#define CLOCK_CPUCLK_DIV 1U
#define CLOCK_FOFI_CALIBRATION_MODE XMC_SCU_CLOCK_FOFI_CALIBRATION_MODE_FACTORY
#define CLOCK_OSCHP_ENABLED 1U
#define CLOCK_OSCHP_MODE XMC_SCU_CLOCK_OSCHP_MODE_OSC
#define CLOCK_PERICLK_DIV 1U
#define CLOCK_SYSPLL_ENABLED 1U
#define CLOCK_SYSPLL_SEL XMC_SCU_CLOCK_SYSPLLCLKSRC_OSCHP
#define CLOCK_SYSPLL_MODE XMC_SCU_CLOCK_SYSPLL_MODE_NORMAL
#define CLOCK_SYSPLL_PDIV 1U
#define CLOCK_SYSPLL_NDIV 24U
#define CLOCK_SYSPLL_KDIV 1U
#define CLOCK_RTCCLK_SEL XMC_SCU_HIB_RTCCLKSRC_OSI
#define CLOCK_STDBYCLK_SEL XMC_SCU_HIB_STDBYCLKSRC_OSI
#define CLOCK_SYSCLK_SEL XMC_SCU_CLOCK_SYSCLKSRC_PLL
#define CLOCK_SYSCLK_DIV 4U

void SystemCoreClockSetup(void)
{
  XMC_SCU_CLOCK_CONFIG_t clock_config =
  {
  #if defined(CLOCK_SYSPLL_ENABLED)
    .syspll_config.n_div = CLOCK_SYSPLL_NDIV,
    .syspll_config.p_div = CLOCK_SYSPLL_PDIV,
    .syspll_config.k_div = CLOCK_SYSPLL_KDIV,
    .syspll_config.clksrc=CLOCK_SYSPLL_SEL,
    .syspll_config.mode = CLOCK_SYSPLL_MODE,
  #else
    .syspll_config.mode = XMC_SCU_CLOCK_SYSPLL_MODE_DISABLED,
  #endif
  #if defined(CLOCK_OSCHP_ENABLED)
    .enable_oschp = true,
  #endif
  #if defined(CLOCK_OSCLP_ENABLED)
    .enable_osculp = true,
  #endif
    .calibration_mode = CLOCK_FOFI_CALIBRATION_MODE,
    .fstdby_clksrc=CLOCK_STDBYCLK_SEL,
    .fsys_clksrc=CLOCK_SYSCLK_SEL,
    .fsys_clkdiv = CLOCK_SYSCLK_DIV,
    .fcpu_clkdiv = CLOCK_CPUCLK_DIV,
  #if defined(CLOCK_CCUCLK_ENABLED)
    .fccu_clkdiv = CLOCK_CCUCLK_DIV,
  #endif
    .fperipheral_clkdiv = CLOCK_PERICLK_DIV
  };
 
 #if defined(CLOCK_EXTCLK_ENABLED)
  /* External output source clock */
  XMC_SCU_CLOCK_SetExternalOutputClockSource(CLOCK_EXTCLK_SEL);
  /* External clock divider setting */
  XMC_SCU_CLOCK_SetExternalOutputClockDivider(CLOCK_EXTCLK_DIV);
 #endif
   
  XMC_SCU_CLOCK_Init(&clock_config);
 
  /* RTC source clock */
  XMC_SCU_HIB_SetRtcClockSource(CLOCK_RTCCLK_SEL);
 
 #if defined(CLOCK_USBCLK_ENABLED)
   /* USB/SDMMC source clock */
   XMC_SCU_CLOCK_SetUsbClockSource(CLOCK_USBCLK_SEL);
   /* USB/SDMMC divider setting */
   XMC_SCU_CLOCK_SetUsbClockDivider(CLOCK_USBCLK_DIV);
 #endif
 
 #if defined(CLOCK_USBPLL_ENABLED)
  XMC_SCU_CLOCK_EnableUsbPll();
  XMC_SCU_CLOCK_StartUsbPll(CLOCK_USBPLL_PDIV, CLOCK_USBPLL_NDIV);
 #endif  
 #if defined(CLOCK_ECATCLK_ENABLED)
  /* ECAT source clock */
  XMC_SCU_CLOCK_SetECATClockSource(CLOCK_ECATCLK_SEL);
  /* ECAT divider setting */
  XMC_SCU_CLOCK_SetECATClockDivider(CLOCK_ECATCLK_DIV);
 #endif
 
 #if defined(CLOCK_WDTCLK_ENABLED)
  /* WDT source clock */
  XMC_SCU_CLOCK_SetWdtClockSource(CLOCK_WDTCLK_SEL);
  /* WDT divider setting */
  XMC_SCU_CLOCK_SetWdtClockDivider(CLOCK_WDTCLK_DIV);
 #endif
 
 #if defined(CLOCK_EBUCLK_ENABLED)
  /* EBU divider setting */
  XMC_SCU_CLOCK_SetEbuClockDivider(CLOCK_EBUCLK_DIV);
 #endif 
  #if defined(CLOCK_USBCLK_ENABLED)
  XMC_SCU_CLOCK_EnableClock(XMC_SCU_CLOCK_USB);
 #endif
 #if defined(CLOCK_SDCLK_ENABLED)
  XMC_SCU_CLOCK_EnableClock(XMC_SCU_CLOCK_MMC);
 #endif
 #if defined(CLOCK_ETHCLK_ENABLED)
  XMC_SCU_CLOCK_EnableClock(XMC_SCU_CLOCK_ETH);
 #endif
 #if defined(CLOCK_EBUCLK_ENABLED)
  XMC_SCU_CLOCK_EnableClock(XMC_SCU_CLOCK_EBU);
 #endif
 #if defined(CLOCK_CCUCLK_ENABLED)
  XMC_SCU_CLOCK_EnableClock(XMC_SCU_CLOCK_CCU);
 #endif
 #if defined(CLOCK_WDTCLK_ENABLED)
  XMC_SCU_CLOCK_EnableClock(XMC_SCU_CLOCK_WDT);
 #endif
}

 

 

 

The following steps show how to get the 19200 bps baud rate.

For example:

The peripheral clock is 72Mhz.

1: Set the sample point:

Sample_point=8

 

 

__STATIC_INLINE void XMC_UART_CH_SetSamplePoint(XMC_USIC_CH_t *const channel, const uint32_t sample_point)
{
  channel->PCR_ASCMode = (uint32_t)((channel->PCR_ASCMode & (uint32_t)(~USIC_CH_PCR_ASCMode_SP_Msk)) |
                                    (sample_point << USIC_CH_PCR_ASCMode_SP_Pos));
}

 

 

2: SetFractionalDivider:(Fractional mode selected and step set the value 1017)

 

 

__STATIC_INLINE void XMC_USIC_CH_SetFractionalDivider(XMC_USIC_CH_t *const channel, const XMC_USIC_CH_BRG_CLOCK_DIVIDER_MODE_t mode, const uint16_t step)
{
  channel->FDR = mode | step;
}

 

 

Mode=32768

Step=1017

  channel->FDR = mode | step;

LinglingG_46_0-1704783410829.png

 

3: The the ASC module get the input clock fpin

Fpin= Fperi/(1023/step)=72000000/(1023/1017)=72000000/1.0058997 =71577712

 

 

void XMC_USIC_CH_SetBaudrateDivider(XMC_USIC_CH_t *const channel, 
                                    XMC_USIC_CH_BRG_CLOCK_SOURCE_t clksel,
                                    bool pppen,
                                    uint32_t pdiv,
                                    XMC_USIC_CH_BRG_CTQSEL_t ctqsel,
                                    uint32_t pctq,
                                    uint32_t dctq)
{
    uint32_t regval = channel->BRG;
    regval &= (uint32_t)~(USIC_CH_BRG_CLKSEL_Msk | USIC_CH_BRG_PPPEN_Msk | USIC_CH_BRG_PDIV_Msk | USIC_CH_BRG_CTQSEL_Msk | USIC_CH_BRG_PCTQ_Msk | USIC_CH_BRG_DCTQ_Msk);
    regval |= clksel | (pppen ? USIC_CH_BRG_PPPEN_Msk : 0) | (pdiv << USIC_CH_BRG_PDIV_Pos) | ctqsel | (pctq << USIC_CH_BRG_PCTQ_Pos) | (dctq << USIC_CH_BRG_DCTQ_Pos);
    channel->BRG = regval;
}

 

 

 

LinglingG_46_1-1704783410833.png

 

4: Then we can refer the below screen to get the baud rate:

FASC=71577712/(233*16) =19200bps

LinglingG_46_2-1704783410842.png

 

It is recommended that you can use the component or the lib to achieve the function first, then depending the successful project to do the developing.

Last but not least, we can refer to the XMC4500 reference manual  here .

Hope it can be helpful for you to have a deep understanding of the baud rate generating.

 

 

 

 

0 Likes
Ahlan
Level 1
Level 1
First reply posted First question asked Welcome!

I disagree that this problem is solved.
All you have done is told me to use XMC which is not an option.
I understand that using XMC is recommenced and indeed I can get an application to work correctly if I use Dave and the Xmc libraries but I can't reproduce the same thing using my own code.
I have studied the XMC library and the 4500 Reference manual and tried to reproduce the functionality using my own code. This strategy normally works and indeed I do get data out of the ASC just at the wrong baudrate.
I believe I have programmed the ASC correctly so this suggests that fPeriph is at 24MHz rather that the expected 120Mhz.
I don't see how this is possible, but evidently it is.
What I am looking for is for someone to suggest what I might be doing wrong.
What might I have not done correctly or forgotten to do in order the fPeriph is at 24Mhz?

0 Likes
LinglingG_46
Moderator
Moderator
Moderator
500 solutions authored 1000 replies posted 10 questions asked

Hi,

Could you share your test project here?

Thanks,

Lingling

0 Likes