Overclock STM32F4 device up to 250MHz
http://stm32f4-discovery.com/2014/11/overclock-stm32f4-device-up-to-250mhz/
Let’s test what STM32F4xx devices can do.
I have all “4 speed families” at home so why not to try it how fast we can go.
By default, for those who don’t know max frequencies for STM32F4xx devices, they are in list below:
- 84MHz: STM32F401 MCUs, including Nucleo-F401 board
- 100MHz: STM32F411 MCUs, including Nucleo F411 board
- 168MHz: STM32F405/7 and STM32F415/17 MCUs, including STM32F4-Discovery board
- 180MHz: STM32F427/29 and STM32F437/39 MCUs, including STM32F429-Discovery board
Ok, we have everything provided, let’s test how far we can go with PLL settings.
First we have to go through, how to set PLL parameters to even get any clock.
Step by step on how PLL works.
About PLL settings
- You gave him some input frequency, let’s say HSE_VALUE = 8MHz.
Then, he divide this by PLL_M factor, that we get 1MHz in the first stage output. This meansPLL_M = HSE_VALUE (in Hz) / 1MHz = / =
- Then, PLL multiplies output (1MHz) with a large number, factor is called PLL_N.
This number depends on STM32F4xx family.
By default, for normal clocks (specified in datasheet) values are:- 84MHz: PLL_N = 336
- 100MHz: PLL_N = 400
- 168MHz: PLL_N = 336
- 180MHz: PLL_N = 360
Probably your question is why so strange values.
Simple answer, STM32F4xx have different peripherals (SDIO, USB, etc)
and some specific peripherals needs exact clock.
If you want to have 168MHz core clock and then for USB 48MHz, this is not possible,
because you cannot set a prescaler of 168/48 = 3.5.
This is “no go”. For that purpose, least common value for (in this case) 168MHz and 48MHz is used, 336.PLL_VCO = PLL_N * (HSE_VALUE / PLL_M)
Note:
PLL_N parameter can be set between 192 and 432.
At least datasheet says that but we will see that we can go more that this. - Ok, we have 336MHz somewhere inside PLL now.
Now become 2 new PLL parameters.- PLL_P: This parameter is used to set system core clock for MCU.
If you want 168MHz clock, and you have 336MHz on the input of this divider,
you set parameter PLL_P = 2. Equation isSYSCLK = PLL_VCO / PLL_P = 336MHz / = 168MHz
- 84MHz: PLL_P = 4
- 100MHz: PLL_P = 4
- 168MHz: PLL_P = 2
- 180MHz: PLL_P = 2
- PLL_Q: This parameter is used to set clock for special peripheral (SDIO, USB, RNG)
to be at least about 48MHz. But this is not always possible.
It divides the input frequency for special peripherals like PLL_P does for system core clock.CLOCK_48MHz = PLL_VCO / PLL_Q = 336MHz / = 48MHz
By default this parameter is set to 7.
If we take a look at what happens if we have 180MHz clock and PLL_N set to 360,
the our PLL_VCO is 360MHz and our “48MHz” clock becomes:CLOCK_48MHz = 360MHz / = .7MHz
It’s not a big problem but yeah, if we want perfect, then if we use USB/SDIO/RNG
we can not have 180MHz for our MCU.
We have to slow it down to 168MHz by setting PLL_N to 336.
Someone will probably say that we can increase PLL_N to 384 and then PLL_Q to 8 and we will getCLOCK_48MHz = 384MHz / = 48MHz
This is true, but if we set PLL_N to 384, then on divide by 2 for PLL_P we have higher frequency
than 180MHz for Core clock (384MHz / 2 = 192MHz) and this is not good now.Terrible If you have 100MHz core clock, then you have PLL_N set to 400 and PLL_Q to 7,wow, that more than 55MHz for peripheral, not good at all.Even PLL_Q = 8 is too small. You need then about 8.3 prescaler but floating points in prescalers = no go.
- PLL_P: This parameter is used to set system core clock for MCU.
- If we now make a full equatons for system core clock, we will get something like this:
PLL_VCO = ((HSE_VALUE / PLL_M) * PLL_N)
SYSTEM_CORE_CLOCK = PLL_VCO / PLL_P
CLOCK_48MHZ = PLL_VCO / PLL_Q - All these settings are set in system_stm32f4xx.c file if you use Standard Peripheral Drivers like I do.
Overclocking STM32F4xx device
To test how far I can go, I used my PWM library hich automatically sets timer period and prescaler
according to the timer’s frequency and pwm frequency you choose.
This values are stored in my working struct for PWM library.
I used this PWM output to measure actual frequency with oscilloscope.
First, I tried overclock STM32F429-Discovery board.
For first test, it was just good if I set PLL_N to higher value.
I set it to PLL_N = 400, and if we calculate this, we will get SYSCLK = 200MHz.
This is more than 180MHz so we can expect any problems. I’ve also set variable
SystemCoreClock = 200000000
to be sure my settings are OK in file.
Then I’ve started my program in debug mode and set timer settings and PWM output.
I’ve measured real 10kHz PWM output like I set.
I was still not sure if this is ok. In debug window, you can look at variables.
Like I previously said, my PWM struct stores information about timer prescaler and period.
I read from debug windows values below:
- Period: 10000
- Absolute value how much ticks timer has to make. Value stored in TIM’s register is Period – 1
- Prescaler: 1
- Absolute value to use with calculations. Value stored in TIM’s register is Prescaler – 1
It was strange for me first time, because this was not so nice result.
Then I realized, that TIM2 for PWM is connected to APB1 bus,
which clock frequency is on F429 APB1 = SYSCLK / 4
but TIM has internal PLL which increases frequency by 2,
so you get TIM2_TICK_DEFAULT = SYSCLK / 4 * 2 = SYSCLK / 2 = 100MHz.
This result is better now. because you get:
PWM_FREQ = TIMER_TICK_DEFAULT_FREQ / (Absolute_Period * Absolute_Prescaler) = 10kHz
PWM_FREQ = TIMER_TICK_DEFAULT_FREQ / ((Period_in_Register + ) * (Prescaler_in_Register + ))
So I was doing this a lot of times, trying different frequencies.
To 250MHz on STM32F429-Discovery I got frequency on my oscilloscope 10kHz and parameters for timer were valid.
So clock was really 250MHz.
For other boards, I got maximum clocks of:
- STM32F429-Discovery; 250MHz
- APB1 = SYSCLK / 4; TIM2 default frequency = SYSCLK / 4 * 2 = 125MHz
- STM32F4-Discovery: 250MHz
- APB1 = SYSCLK / 4; TIM2 default frequency = SYSCLK / 4 * 2 = 125MHz
- Nucleo F401: 125MHz
- APB1 = SYSCLK / 2; TIM2 default frequency = SYSCLK / 2 * 2 = 125MHz
- Nucleo F411: 125MHz
- APB1 = SYSCLK / 2; TIM2 default frequency = SYSCLK / 2 * 2 = 125MHz
Important notes:
- There is no guarantee that every MCU in the series will go to the value like my did, because they are not designed for so high speed,
- I do not suggest you that you use this in production
- When frequency is higher than expected, MCU can become unstable and can crash or some hardfault error can happen,
- Also, temperature rises with frequency.
- You can blow your MCU
- I’m not responsible for that. You are doing this on your own risk.
PLL Settings
These settings are set in system_stm32f4xx.c file
/************************* PLL Parameters *************************************/
#if defined (STM32F40_41xxx) || defined (STM32F427_437xx) || defined (STM32F429_439xx) || defined (STM32F401xx)
/* PLL_VCO = (HSE_VALUE or HSI_VALUE / PLL_M) * PLL_N */
#define PLL_M 8
#else /* STM32F411xE */
#if defined (USE_HSE_BYPASS)
#define PLL_M 8
#else /* STM32F411xE */
#define PLL_M 16
#endif /* USE_HSE_BYPASS */
#endif /* STM32F40_41xxx || STM32F427_437xx || STM32F429_439xx || STM32F401xx */ /* USB OTG FS, SDIO and RNG Clock = PLL_VCO / PLLQ */
#define PLL_Q 7 #if defined (STM32F40_41xxx)
#define PLL_N 500
/* SYSCLK = PLL_VCO / PLL_P */
#define PLL_P 2
#endif /* STM32F40_41xxx */ #if defined (STM32F427_437xx) || defined (STM32F429_439xx)
#define PLL_N 500 /* 250MHz clock for STM32F429-Discovery board */
/* SYSCLK = PLL_VCO / PLL_P */
#define PLL_P 2
#endif /* STM32F427_437x || STM32F429_439xx */ #if defined (STM32F401xx)
#define PLL_N 500
/* SYSCLK = PLL_VCO / PLL_P */
#define PLL_P 4
#endif /* STM32F401xx */ #if defined (STM32F411xE)
#define PLL_N 500
/* SYSCLK = PLL_VCO / PLL_P */
#define PLL_P 4
#endif /* STM32F411xx */ /******************************************************************************/ /**
* @}
*/ /** @addtogroup STM32F4xx_System_Private_Macros
* @{
*/ /**
* @}
*/ /** @addtogroup STM32F4xx_System_Private_Variables
* @{
*/ #if defined (STM32F40_41xxx)
uint32_t SystemCoreClock = ;
#endif /* STM32F40_41xxx */ #if defined (STM32F427_437xx) || defined (STM32F429_439xx)
uint32_t SystemCoreClock = ; /* 250MHz clock */
#endif /* STM32F427_437x || STM32F429_439xx */ #if defined (STM32F401xx)
uint32_t SystemCoreClock = ;
#endif /* STM32F401xx */ #if defined (STM32F411xE)
uint32_t SystemCoreClock = ;
#endif /* STM32F401xx */
Main
Main program
/**
* Keil project for overclocking STM32F4xx devices
*
* Before you start, select your target, on the right of the "Load" button
*
* @author Tilen Majerle
* @email tilen@majerle.eu
* @website http://stm32f4-discovery.com
* @ide Keil uVision 5
* @packs STM32F4xx Keil packs version 2.2.0 or greater required
* @stdperiph STM32F4xx Standard peripheral drivers version 1.4.0 or greater required
*
* When you use debug, you need to print "PWM_Data" variable to see results
*/
/* Include core modules */
#include "stm32f4xx.h"
/* Include my libraries here */
#include "defines.h"
#include "tm_stm32f4_delay.h"
#include "tm_stm32f4_disco.h"
#include "tm_stm32f4_pwm.h" int main(void) {
/* Timer settings struct */
TM_PWM_TIM_t PWM_Data; /* Initialize system */
SystemInit(); /* Initialize delay */
TM_DELAY_Init(); /* Initialize leds on board */
TM_DISCO_LedInit(); /* Turn on all leds */
TM_DISCO_LedOn(LED_GREEN); /* Init Timer for PWM, TIM frequency 10kHz */
TM_PWM_InitTimer(TIM2, &PWM_Data, ); /* Initialize PWM Channel 1 on TIM2, PinsPack 2 = PA5 */
TM_PWM_InitChannel(TIM2, TM_PWM_Channel_1, TM_PWM_PinsPack_2); /* Set 70% duty cycle */
TM_PWM_SetChannelPercent(TIM2, &PWM_Data, TM_PWM_Channel_1, ); while () { }
}
Project below has settings in system_stm32f4xx.c
set to maximum frequency like I said above, so 250 and 125MHz.
Before you debug in Keil uVision, you have to rebuild. All libs are included in project.
Overclock STM32F4 device up to 250MHz的更多相关文章
- STM32F4 External interrupts
STM32F4 External interrupts Each STM32F4 device has 23 external interrupt or event sources. They are ...
- STM32F4 HAL Composite USB Device Example : CDC + MSC
STM32F4 USB Composite CDC + MSC I'm in the process of building a USB composite CDC + MSC device on t ...
- STM32F4读写内部FLASH【使用库函数】
STM32F4Discovery开发帮使用的STM32F407VGT6芯片,内部FLASH有1M之多.平时写的代码,烧写完之后还有大量的剩余.有效利用这剩余的FLASH能存储不少数据.因此研究了一下S ...
- One-wire Demo on the STM32F4 Discovery Board
One-wire Demo on the STM32F4 Discovery Board Some of the devs at work were struggling to get their s ...
- VGA Output from STM32F4 Discovery board
VGA Output from STM32F4 Discovery board I love the web! There are so many cool projects out there, a ...
- STM32F4编程手册学习2_内存模型
STM32F4编程手册学习2_内存模型 1. 内存映射 MCU将资源映射到一段固定的4GB可寻址内存上,如下图所示. 内存映射将内存分为几块区域,每一块区域都有一个定义的内存类型,一些区域还有一些附加 ...
- stm32F4中断分析-HAL库
详细可以参考: STM32使用HAL库操作外部中断——实战操作 https://www.cnblogs.com/wt88/p/9624103.html /** ******************** ...
- Linux系统中的Device Mapper学习
在linux系统中你使用一些命令时(例如nmon.iostat 如下截图所示),有可能会看到一些名字为dm-xx的设备,那么这些设备到底是什么设备呢,跟磁盘有什么关系呢?以前不了解的时候,我也很纳闷. ...
- 使用STM32F4的CCM内存
使用STM32F4的CCM内存http://www.stmcu.org/module/forum/forum.php?mod=viewthread&tid=604814&fromuid ...
随机推荐
- 第11月第23天 markedTextRange 崩溃
1. 在对textView.textField限制文字长度时,如果不做特殊处理,当联想文字加上已输入文字超出设定长度时,iOS 7.0系统会崩溃(ios 8.0以上系统做了处理,不会崩溃). http ...
- 转载 python多重继承C3算法
备注:O==object 2.python-C3算法解析: #C3 定义引用开始 C3 算法:MRO是一个有序列表L,在类被创建时就计算出来. L(Child(Base1,Base2)) = [ Ch ...
- Mysql字符集介绍
- 【干货】Linux内存数据的获取与转存 直捣密码
知识源:Unit 2: Linux/Unix Acquisition 2.1 Linux/Unix Acquistion Memory Acquisition 中的实验demo部分 小白注意,这是网 ...
- GaN助力运营商和基站OEM实现5G sub-6GHz和mmWave大规模MIMO
到2021年,估计全球会有更多的人拥有移动电话(55亿),将超过用上自来水的人数(53亿).与此同时,带宽紧张的视频应用将进一步增加对移动网络的需求,其会占移动流量的78%.使用大规模多输入多输出(M ...
- zabbix3.0.4安装趋势图集中显示插件graphtrees
通过yum方式安装的zabbix 1.将/usr/share/zabbix目录修改权限,因此处我们使用的是apache,所以用户改为apache,如果是nginx需要改为nginx(是否需要修改可以参 ...
- 基于Apache在本地配置多个虚拟主机站点
简单的说,打开httpd.conf 在最后加入如下内容: <VirtualHost 127.0.0.2:80> DocumentRoot d:/AppServ/www2 Ser ...
- pwd、ln和重定向命令
pwd命令 命令功能: 使用pwd命令可以显示当前的工作目录,该命令很简单,直接输入pwd即可,后面不带参数. pwd命令以绝对路径的方式显示用户当前工作目录.命令将当前目录的全路径名称(从根 ...
- 今天我碰到了由于web.xml文件表头信息导致润乾报表启动失败的问题,解决方案如下
下面是从2.3,2.4.2.5 3.0集中版本的web.xml头信息的细节,当发现系统启动不报错但是该生成的功能没有正常生成,特别是在这次配置润乾报表的时候发现用2.4版本的时候,在web.xml中配 ...
- HDU 2200 Eddy's AC难题
解析: 1.可以从中任选m个人(n=>m>=2),有Cn(m)中选择; 2.再把这m个人分2组(每个人都要分组),要使满足最小ac数大于最大ac数,只需要在m个人中插板即可: 例如: m个 ...