51单片机的准确延时分析

首先我们来看个简单的例子


51#include "reg52.h"			 //此文件中定义了单片机的一些特殊功能寄存器
typedef unsigned int u16;	  //对数据类型进行声明定义
typedef unsigned char u8;
sbit led=P2^0;		 //将单片机的P2.0端口定义为led
void delay(u16 i)
{
	while(i--);	
}
void main()
{
	while(1)
	{
		led=0;
		delay(50000); //大约延时450ms
		led=1;
		delay(50000); //大约延时450ms	
	}		
}

我们使用keil的反汇编功能,将关键的延时代码转换为汇编语言,因为汇编语言可以精确的算出延时时间

  29: void main() 
    30: { 
    31:         while(1) 
    32:         { 
    33:                 led=0; 
C:0x0800    C2A0     CLR      led(0xA0.0)
    34:                 delay(50000); //大约延时450ms 
C:0x0802    7F50     MOV      R7,#0x50
C:0x0804    7EC3     MOV      R6,#0xC3
C:0x0806    120820   LCALL    delay(C:0820)
    35:                 led=1; 
C:0x0809    D2A0     SETB     led(0xA0.0)
    36:                 delay(50000); //大约延时450ms    
C:0x080B    7F50     MOV      R7,#0x50
C:0x080D    7EC3     MOV      R6,#0xC3
C:0x080F    120820   LCALL    delay(C:0820)
    37:         }               
C:0x0812    80EC     SJMP     main(C:0800)
C:0x0814    787F     MOV      R0,#0x7F
C:0x0816    E4       CLR      A
C:0x0817    F6       MOV      @R0,A
C:0x0818    D8FD     DJNZ     R0,C:0817
C:0x081A    758107   MOV      SP(0x81),#0x07
C:0x081D    020800   LJMP     main(C:0800)
    18: void delay(u16 i) 
    19: { 
    20:         while(i--);      
C:0x0820    EF       MOV      A,R7
C:0x0821    1F       DEC      R7
C:0x0822    AC06     MOV      R4,0x06
C:0x0824    7001     JNZ      C:0827
C:0x0826    1E       DEC      R6
C:0x0827    4C       ORL      A,R4
C:0x0828    70F6     JNZ      delay(C:0820)
    21: } 

我在这里大致画出了这段代码的流程图
在这里插入图片描述
然后计算关键代码的时间

 void delay(u16 i) 
  { 
    while(i--);      
0x0820    EF          MOV      A,R7                                 1
0x0821    1F           DEC       R7                                 1
0x0822    AC06     MOV       R4,0x06                                1
0x0824    7001      JNZ       C:0827                                2
0x0826    1E          DEC        R6                                (1)
0x0827    4C          ORL       A,R4                                2           
0x0828    70F6      JNZ       delay(C:0820)                         2
    } 

可以算出总计为:1+1+1+2+2+2=9(机器周期)
总时间等于 50000*9=450000(机器周期)约等于450ms

80C51单片机外接了一个11.0592M的晶体振荡器,那我们就说这个单片机系统的时钟周期是1/11.0592M,8051系列单片机的的时钟频率是晶振频率的12分频,一个机器周期约为1us

然后我们再来看一段带有循环功能的延时代码

void delay(uint z)
{
	uint x,y;
	for(x = z; x > 0; x--)
		for(y = 120; y > 0 ; y--);
}
	delay(1000); //延时1000毫秒

我们将其翻译成机器语言
循环部分:
小循环y


C:0x0842    ED        MOV       A,R5                            1                          
C:0x0843    1D         DEC        R5                            1                          
C:0x0844    7001     JNZ       C:0847                           2                                             C:0x0846    1C         DEC        R4                           (1)                                           
C:0x0847    ED        MOV      A,R5                             1                           
C:0x0848    4C        ORL        A,R4                           1                                         
C:0x0849    70F7    JNZ       C:0842                            2                            
总时间:1+1+2+1+1+2=8(机器周期)  
`
大循环
```csharp

  (C:0x082A    7FE8     MOV      R7,#0xE8
   C:0x082C    7E03     MOV      R6,#0x03)
C:0x083E    7D01     MOV      R5,#0x78                          1      
C:0x0840    7C00     MOV      R4,#0x00                          1
C:0x0835    D3         SETB     C                               1                         
C:0x0836    EF         MOV      A,R7                            1
C:0x0837    9400     SUBB      A,#0x00                          1
C:0x0839    EE         MOV       A,R6                           1 
C:0x083A    9400     SUBB     A,#0x00                           1
C:0x083C    4014      JC          C:0852                        2
【小循环】 
C:0x084B    EF         MOV      A,R7                            1                        
C:0x084C    1F          DEC      R7                             1                        
C:0x084D    70E6     JNZ      delay(C:0835)                     2                        

总时间:1+1+1+1+1+1+1+2+1+1+2=13(机器周期)

循环总时间={13+8*(小循环次数)}大循环次数
=(13+8
120)*1000
=973000 约等于1000us

ok

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值