目录

1.接线图

2.Keil的Debug环境配置

3.代码部分

4.打开Debug调试界面

5.拓展实验

6.结束语(程序源码)


"昨天同学问我:‘兄弟,调PWM必须要有示波器吗?’
都叫我兄弟了那还说啥,我当着他的面在Keil里按下F5——
刹那间,PWM波形像音乐频谱般在屏幕上跳动起来!


前言:在嵌入式开发中,PWM波形的调试效率直接影响电机控制、电源管理等关键功能的开发周期。传统示波器虽能提供高精度波形,但接线复杂、设备成本高昂;Keil5内置的逻辑分析仪则通过SWD协议实现无接触测量,却存在带宽限制。本文将通过实测数据(包括1MHz PWM捕获对比、上升时间测量误差分析等),揭示两种工具的适用边界,并给出『硬件调试黄金法则』:当信号频率>200kHz时必须切换示波器,而代码级调试优先使用Keil。助你节省70%以上的硬件调试时间。

 使用的芯片型号是STM32F103C8T6(师承江协科技!!)

因为只是简单的观测PWM波形,所以使用的材料只有一个芯片和ST-Link(有仿真功能即可)


 1.接线图


 2.Keil的Debug环境配置

1.点击魔术棒(四面楚歌这个图标)

 2.单击Debug

3.勾选Use Simulator(使用软件仿真)Limit Speed to Real-Time(限制CPU模拟的速度与实际时间同步)

 

 4.根据芯片填写Dialog和Parameter(我使用的是STM32F103C8T6)*四个空都要填!!!

依次填入DARMSTM.DLL,-pSTM32F103C8,TRAMSTM.DLL,-pSTM32F103C8

然后单击OK

建议复制 

 3.代码部分

 我使用的是TIM1,是高级定时器,所以必须要加入这一行代码才能输出PWM波形!!!

PA11---->TIM1_CH4(高级定时器1的通道4)

TIM_CtrlPWMOutputs(TIM1,ENABLE);//高级定时器专属--MOE主输出使能
#include "PWM.h"

/**
 * @brief 初始化驱动电机的PWM定时器
 * @param arr:自动重装载值(决定PWM频率)
 * @param psc:预分频系数(决定PWM频率)
 */
void PWM_Init_TIM1(u16 Psc,u16 Per)
{
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_TIM1,ENABLE);//开启时钟
	
	GPIO_InitTypeDef GPIO_InitStruct;
	GPIO_InitStruct.GPIO_Mode=GPIO_Mode_AF_PP;	//初始化GPIO--PA11为复用推挽输出
	GPIO_InitStruct.GPIO_Pin=GPIO_Pin_11;
	GPIO_InitStruct.GPIO_Speed=GPIO_Speed_50MHz;
	GPIO_Init(GPIOA,&GPIO_InitStruct);
	
	TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStruct;
	TIM_TimeBaseInitStruct.TIM_ClockDivision=TIM_CKD_DIV1;
	TIM_TimeBaseInitStruct.TIM_CounterMode=TIM_CounterMode_Up;
	TIM_TimeBaseInitStruct.TIM_Period=Per;
	TIM_TimeBaseInitStruct.TIM_Prescaler=Psc;
	TIM_TimeBaseInit(TIM1,&TIM_TimeBaseInitStruct);
	
	TIM_OCInitTypeDef TIM_OCInitStruct;
	TIM_OCInitStruct.TIM_OCMode=TIM_OCMode_PWM1;//初始化输出比较
	TIM_OCInitStruct.TIM_OCPolarity=TIM_OCPolarity_High;
	TIM_OCInitStruct.TIM_OutputState=TIM_OutputState_Enable;
	TIM_OCInitStruct.TIM_Pulse=0;
	TIM_OC4Init(TIM1,&TIM_OCInitStruct);
	
	TIM_CtrlPWMOutputs(TIM1,ENABLE);//高级定时器专属--MOE主输出使能

	TIM_OC4PreloadConfig(TIM1,TIM_OCPreload_Enable);//ENABLE//OC4预装载寄存器使能
	TIM_ARRPreloadConfig(TIM1,ENABLE);//TIM1在ARR上预装载寄存器使能
	
	TIM_Cmd(TIM1,ENABLE);//开定时器。
}


/**
  * @brief PWM设置CCR
  * @param	Compare 要写入的CCR的值
  * @Notice CCR和ARR共同决定占空比,此函数仅设置CCR的值,并不直接是占空比
  *           占空比Duty = CCR / (ARR + 1)
  */
void PWM_SetCompare(uint16_t Compare)
{
   TIM_SetCompare4(TIM1, Compare);		//设置CCR4的值
}

 PWM.h代码

#ifndef  __PWM_H
#define  __PWM_H

#include "stm32f10x.h"                  // Device header


void PWM_Init_TIM1(u16 Psc,u16 Per);
void PWM_SetCompare(uint16_t Compare);


#endif

 主程序代码

#include "stm32f10x.h"                  // Device header
#include "PWM.h"

int main(void)
{  		

    PWM_Init_TIM1(72-1, 1000-1);		//(PSC,ARR)第一个是预分频值,第二个是自动重装载值
    PWM_SetCompare(500);    			//设置CCR的值,占空比Duty = CCR / (ARR + 1)
    
    while(1)
    {

    }
}

 4.打开Debug调试界面

1.点击Start Debug Session或(Ctrl+F5)

2.单击Setup.....

 

3.点击这个虚线小方框

 4.输入我们需要观察的引脚(Portx.xx,不区分大小写)

因为我们本次需要观测的是PA11引脚 ,所以输入Porta.11然后后回车,再点击Close

 

5.点击全速运行代码(Run或F5)

 

接下来就可以观察自己的脉冲波形的占空比(可以用鼠标滚轮压缩/扩展最小时间网格Grid)

在一个周期内,高电平所占的时间与整个周期时间的比率叫占空比

 ARR值为1000-1,CCR的值为500

占空比为:\text{Duty\%} = \left( \frac{\text{CCR}}{\text{ARR} + 1} \right) \times 100\%则占空比为50%

取一个周期中的上升沿开始时间为6.017944ms

 再取到下一个上升沿的时间为6.685167ms

 则得到一个周期的时间为6.685167ms-6.017944ms=0.667223ms

通过取下降沿时间可以得到高电平的时间为6.685167ms-6.3515555ms

 则占空比为\frac{6.685167 \times 10^{-3} - 6.3515555 \times 10^{-3}}{6.685167 \times 10^{-3} - 6.017944 \times 10^{-3}}=50%

实验符合预期


5.拓展实验

若是要实现呼吸灯PID这一类需要对PWM时时刻刻进行改变的程序,Keil能否快速且准确的观察到波形呢??

主程序略微修改一下,动态循环修改占空比,再仔细观察波形图

主程序代码部分

#include "stm32f10x.h"                  // Device header
#include "PWM.h"
#include "Delay.h"

uint8_t i;

int main(void)
{  		

   PWM_Init_TIM1(720-1, 100-1);		//(PSC,ARR)第一个是预分频值,第二个是自动重装载值
//   PWM_SetCompare(500);    			//设置CCR的值,占空比Duty = CCR / (ARR + 1)
   
   while(1)
    {
			for (i = 0; i <= 100; i++)
				{
					PWM_SetCompare(i);			//依次将定时器的CCR寄存器设置为0~100,PWM占空比逐渐增大
					Delay_ms(10);				//延时10ms
				}
				for (i = 0; i <= 100; i++)
				{
					PWM_SetCompare(100 - i);	//依次将定时器的CCR寄存器设置为100~0,PWM占空比逐渐减小
					Delay_ms(10);				//延时10ms
				}
    }
}

点击编译后进入Debug模式(否则修改无效)

观察图像,速度略快,但是还是能清晰的看见keil内部逻辑分析仪的真实有效性


 6.结束语(程序源码)

好了,希望这篇教程能够帮助你更好地掌握Keil Debug的使用方法,如果有什么不对的地方欢迎留言指正,一起享受嵌入式的乐趣!!
链接: https://pan.baidu.com/s/1nlekTi1v5DSXprBc58J9Qw 提取码: JCY1

Logo

openvela 操作系统专为 AIoT 领域量身定制,以轻量化、标准兼容、安全性和高度可扩展性为核心特点。openvela 以其卓越的技术优势,已成为众多物联网设备和 AI 硬件的技术首选,涵盖了智能手表、运动手环、智能音箱、耳机、智能家居设备以及机器人等多个领域。

更多推荐