Hc32f460 MCU Clock Speed Issue/Bug

Basic Information:

Printer Model: Anycubic Kobra Neo
MCU / Printerboard: TriGorilla V_3.0.6 (Pi Zero 2 W as Klipper Host)
klippy.log (3.2 MB)
N.B The klippy log attached is my most recent log where my firmware has been flashed back to 168Mhz for testing purposes and another “MCU Timer too close” error occured.

Describe your issue:

I had been experiencing some intermittent issues with the “MCU Timer to close” issue causing quite a few prints to fail. Initially I had flashed my firmware for the hc32f460 with a clock speed of 168Mhz as this was the default. After some attempted internet “research”, I seemed to find that the clock speed of the Arm chip included on the stock MCU runs at 200Mhz, so decided to reflash my firmware with that option instead.

On the plus side it completely resolved the “MCU Timer too close” issue, and I have not had this occur once since I switched to 200Mhz.

On the downside there are some other strange side effects that seem to have occurred. Firstly the fans and stepper motors all seem to sound a little different and move speeds are not the same as when using 168Mhz (assuming there is some PWM issue here). Secondly, the Mainsail interface still reports the MCU operating with a frequency of 168Mhz even when flashed with 200Mhz firmware.

I’ve seen other people discussing this same issue elsewhere: Neo: part cooling fan issue under Klipper (fan dies) [was: bl_pin ?] · 1coderookie/Klipper4KobraGoNeo · Discussion #2 · GitHub

Is it the case that my MCU is actually only able to run 168Mhz (and if so, why does changing the firmware resolve my “MCU Timer too close” issue)?

Is there a bug somewhere in the Klipper firmware which is not correctly altering some elements for the 200Mhz clock speed?

I can confirm that I have observed this for a while now and been running 200MHz. But with the recent Klipper update that warns if the MCU clock speed is wrong, I brought my attention to this issue as well.

Certainly 200MHz is correct for the Kobra Neo/TriGorilla V_3.0.6 - steppers sound best, no skipped steps, no timer too close errors, but Klipper complains that the frequency is wrong, and Mainsail reports 168MHz, even if it’s compiled for 200. Compiled for 168Mhz, the motor speeds are different, steps are skipped with accels and speeds setup at 200MHz, and the steppers don’t sound healthy…

I’ve tried looking at the Anycubic Kobra Neo marlin fork source code: GitHub - ANYCUBIC-3D/Kobra_Neo , but couldn’t figure out exactly what frequency is used at stock (defined by the bootloader? Kobra_Neo/source/main/hdsc32core/system_hc32f46x.c at 3e43557ccfe29a3e480114045cfb183b028e9475 · ANYCUBIC-3D/Kobra_Neo · GitHub )

So the question remains - where’s the problem? Is it Klipper? Is it the bootloader? Is the correct freq actually 168MHz and if one was running 200MHz, they would have to recalibrate everything for 168, as everything runs at a different speed?

Well, there can be only one truth. Either the MCU is running at 200MHz or at 168MHz.

@Jookia and @SteveGotthardt have been working on this board. Maybe they can chime in.

Different Trigorilla boards have shipped with different default frequencies from the factory. Klipper does not set the clock frequency so you must select 168MHz or 200MHz depending on what your board uses.

It’s possible to write a patch (and I have done it) to set the clock in Klipper according to the MHz option, but you would need to use a fork of Klipper that does that it as it’s not a change mainline would bother with.

I mean, technically :nerd_face:, some MCUs do have DVFS and can dynamically scale their operating frequency.

How would one figure out what freq is set from the factory? Can we trust Klipper if it says that the compiled frequency is wrong? Also, is it possible to change the factory default? Is the freq set in the bootloader, or is it set by hardware, i.e. a crystal or some resistor combination?

You can figure it out by checking one of the OTP registers of the chip. It maybe reconfigurable, I’m not sure- I didn’t look far enough. This value is likely set at the factory by Anycubic or by the HC32F460 manufacturers. The boot ROM probably uses this value to set the system clocks before running the application (Klipper).

I believe you can trust Klipper’s Linux-side measurement very well: Klipper on the microcontroller regularly sends a clock packet to the host containing a timestamp. The host compares this to its own clock and uses this to calculate the actual frequency Klipper is running on.
When the host says your microcontroller is running at 200MHz or 168MHz, that is an actual measurement rather than just self-reported information from the microcontroller.

It is possible to change the clock dynamically at runtime to a specific value that aligns with the Klipper configuration. I have hesitated to do this in my fork as I’m unsure why exactly the values are different. There’s a few reasons why it might be this way:

  • The chip itself doesn’t support 200MHz but has been binned to work at 168MHz. This is the scary option.
  • The chip manufacturer realized running at a higher frequency by default is a waste of power. This is probably the most likely option.
  • Anycubic have decided 168MHz is better for some reason

The Anycubic firmware has this in its changelog:

===================================================== ===============================

V2.8.2_20220905T1717

Firmware
1. Before clock initialization, turn on high performance mode
2. Fixed the problem that the minimum speed is limited to 5mms

UI
1. None

===================================================== ===============================

V2.8.1_20220725T1432

Firmware
1. Reduce the system frequency from 200M to 168M, compatible with 210807N batch
2. Use SRAM1 and SRAM2 instead of SRAMH
3. Optimize the problem of continuous printing after power failure without power failure during normal printing

UI
1. None

So it seems they have decided to run all the Kobras at 168MHz. Again, it’s kind of unclear if this implies the hardware is incapable of running at 200MHz.

Adding this change to Klipper would requre two steps:

  • Telling people to set the clock frequency in the configuration to 168MHz
  • Setting the clock frequency to 168Mhz

If they set the frequency to 200MHz they’ll have the same error as they do now. So you’d have to tell existing Klipper users to update their configuration or their board would break.

Alternatively you could set the clock based on Klipper’s given frequency. But is this safe or a good idea? I’m not sure.


As you can see there’s a lot of questions here. At the end of the day the solution I’ve come up with is for people to do go through the one time problem of setting the frequency for their printer and remembering what it is. It’s a bit of a hurdle for sure.

I’m not really sure, what the topic here actually is.

From my understanding of the above you are reporting:

  • Your MCU is running at 200MHz although Klipper is reporting that 168MHz is correct
  • At 200MHz your board is working well
  • Setting it to 168MHz (as indicated by Klipper) will cause issues

Correct! Hence my confusion - if 168MHz is the correct freq, why is only 200MHz working properly for this board? Something is not right and I was wondering if there is a bug/issue in the code.

I can record some video comparing the behavior of the steppers between the two MCU frequencies to highlight the issue.

Here’s a video comparing 200MHz vs 168MHz. I simply moved the X and Y axes by + and - 100mm, and for the Z axis ±25mm. At 168MHz you can hear how the Y axis struggles. https://www.youtube.com/watch?v=uPTNsQ3YCbk

I guess it is possible that 168MHz is the proper freq, where everything runs at the correct speed, while 200MHz makes everything run slower and that’s why everything sounds healthier, as the printer hardware can handle those physical speeds created by the 200MHz MCU clock. If that’s the case, I would have to reconfigure my max velocities and accels for 168MHz. But I’m not sure though, it could also be the other way around - maybe the physical speeds created by the 200MHz clock is correct?.. and I just keep thinking if there is something wrong on the low-level with those different clocks, and I am just not sure which freq is the correct one for the board. (shouldn’t a higher clock speed produce higher physical stepper motor speeds?)

FWIW, I do not think this is the case.
Regardless if 200 or 168 both are fast enough to drive your speeds and if more steps than available processing power are generated, then Klipper reacts with Rescheduled timer in the past

This would be a catastrophe. The steps and their timing must never relate to the the MCU freq. The total number of steps over all steppers depend on the processing power / clock speed.
You would not want your steppers run 4x faster on 200MHz board compared to a 50MHz board.
Also see above link under “Benchmarks”.

Could you please try this branch of Klipper I made a while back with both clock frequencies: GitHub - printers-for-people/catboat at jookia/clktest It will set the clock at boot the the frequency of your choice (168MHz or 200MHz). Tell me if this fixes your problem. If it does I will clean it up and merge it in to catboat (Klipper fork).

Yes, exactly.

Klipper tracks print timing according to the primary mcu (the one declared as [mcu]). If that one is telling the Klipper host that it is running at 200Mhz while it is actually running at 168Mhz, then the whole system slows down and all your requested speeds are off. (Along with other weird timing issues.) Said another way, if a 100mm move at 100mm/s were to take 1 second, then it would be scheduled for 200 million ticks on the primary mcu, and if the primary mcu actually takes 1.19s to count to 200 million ticks, then the move traverses 100mm in 1.19s which is ~84mm/s - notably slower than requested.

So, best to set the time correctly and then reduce your print speeds to something the motors and axes can reasonably handle.

Cheers,
-Kevin

2 Likes