频率定义为每秒的周期数。它也可以定义为总时间“T”的倒数。在本项目中,我们将计算进入8051微控制器端口3.5的脉冲数,并将其显示在16 * 2 LCD显示屏上。所以基本上我们测量了8051端口3.5的信号频率。这里我们使用了AT89S528051芯片,在非稳定模式下使用555 IC来生成采样脉冲进行演示。
所需组件:
8051 微控制器 (AT89S52)
16*2液晶显示屏
频率源(555 定时器)
电位计
连接线
电路图:
使用 8051 定时器测量频率:
8051微控制器是一款8位微控制器,具有128字节的片上RAM,4K字节的片上ROM,两个定时器,一个串行端口和四个8位端口。8052微控制器是微控制器的扩展。要将端口 3.5 配置为计数器,TMOD 寄存器值设置为 0x51。下图显示了TMOD寄存器。
门 | C / T | M1 | M0 | 门 | C / T | M1 | M2 |
定时器 1 | 定时器 0 |
GATE- 设置 GATE时,仅当 INTx 引脚为高电平且 TRx 控制引脚设置为 TRx 控制引脚时,才会使能定时器或计数器。当 GATE 被清除时,只要 TRx 控制位设置为 U,定时器就会启用。
C / T– 当C / T= 0时,它充当计时器。当 C/T = 1 时,它充当计数器。
M1 和M0表示工作模式。
对于 TMOD = 0x51,定时器1充当计数器,并在模式1(16位)下运行。
16 * 2 LCD用于以赫兹(Hz)显示信号的频率。如果您不熟悉 16x2 LCD,请在此处查看有关 16x2 LCD 引脚及其命令的更多信息。另请查看如何将液晶屏与8051连接。
555定时器作为频率源:
频率源应产生方波,最大幅度限制为5V,因为8051微控制器的端口无法处理大于5V的电压。它可以测量的最大频率为655.35 KHz,因为TH1和TL1寄存器的内存限制(每个8位)。在 100 毫秒内,TH1 和 TL1 最多可容纳 65535 个计数。因此,可以测量的最大频率为 65535 * 10 = 655.35 KHz。
在这个 8051 频率计项目中,我在非稳定模式下使用 555 定时器来产生可变频率方波。555 IC产生的信号频率可以通过调整电位计来改变,如本项目结束时给出的视频所示。
在本项目中,Timer1 (T1) 对进入 8051 微控制器端口 3.5 的脉冲数进行 100 毫秒的计数。计数值将分别存储在 TH1 和 TL1 寄存器中。为了组合TH1和TL1寄存器的值,使用以下公式。
Pulses = TH1 * (0x100) + TL1
现在,“脉冲”将在 100 毫秒内具有周期数。但信号的频率定义为每秒的周期数。要将其转换为频率,请使用以下公式。
Pulses = Pulses * 10
工作和代码解释:
本项目结束时给出了该频率计的完整 C 程序。代码被分成有意义的小块,并在下面解释。
对于与8051微控制器的16 * 2 LCD接口,我们必须定义16 * 2 LCD连接到8051微控制器的引脚。16*2 LCD 的 RS 引脚连接到 P2.7,16*2 LCD 的 RW 引脚连接到 P2.6,16*2 LCD 的 E 引脚连接到 P2.5。数据引脚连接到 8051 微控制器的端口 0。
sbit rs=P2^7;
sbit rw=P2^6;
sbit en=P2^5;
接下来,我们必须定义一些在程序中使用的函数。延迟功能用于创建指定的时间延迟。Cmdwrt功能用于向16 * 2 LCD显示器发送命令。Datawrt功能用于将数据发送到16 * 2 LCD显示器。
void delay(unsigned int) ;
void cmdwrt(unsigned char);
void datawrt(unsigned char);
在代码的这一部分中,我们将命令发送到 16*2 lcd。清除显示、递增光标、强制光标以 1 开头等命令圣在指定的时间延迟后,线被一一发送到16 * 2液晶显示器。
for(i=0;i<5;i++)
{
cmdwrt (cmd[i]);
delay (1);
}
在代码的这一部分中,定时器1配置为计数器,操作模式设置为模式1。
定时器0配置为定时器,操作模式设置为模式1。定时器1用于计算脉冲数,定时器0用于产生延时。TH1 和 TL1 值设置为 0,以确保计数从 0 开始。
TMOD=0x51;
TL1=0;
TH1=0;
在代码的这一部分中,计时器运行 100 毫秒。使用延迟功能生成 100 毫秒的延迟。TR1=1 用于启动计时器,TR1=0 用于在 100 毫秒后停止计时器。
TR1=1;
delay(100);
TR1=0;
在代码的这一部分中,将 TH1 和 TL1 寄存器中存在的计数值组合在一起,然后乘以 10 以获得 1 秒内的总周期数。
Pulses = TH1*(0x100) + TL1;
Pulses = pulses*10;
在代码的这一部分中,频率值被转换为单个字节,以便于在16 * 2 LCD显示器上显示。
d1 = pulses % 10;
s1 = pulses % 100;
s2 = pulses % 1000;
s3 = pulses % 10000;
s4 = pulses % 100000;
d2 = (s1-d1) / 10;
d3 = (s2-s1) / 100;
d4 = (s3-s2) / 1000;
d5 = (s4-s3) / 10000;
d6 = (pulses-s4) / 100000;
在代码的这一部分中,频率值的各个数字被转换为ASCII格式,并显示在16 * 2 LCD显示屏上。
If (pulses>=100000)
datawrt ( 0x30 + d6);
if(pulses>=10000)
datawrt( 0x30 + d5);
if(pulses>=1000)
datawrt( 0x30 + d4);
if(pulses>=100)
datawrt( 0x30 + d3);
if(pulses>=10)
datawrt( 0x30 + d2);
datawrt( 0x30 + d1);
在代码的这一部分中,我们将命令发送到 16*2 LCD 显示器。该命令将复制到 8051 微控制器的端口 0。对于命令写入,RS 设置为低电平。对于写入操作,RW 设置为低电平。在使能 (E) 引脚上施加高到低脉冲以启动命令写入操作。
void cmdwrt (unsigned char x)
{
P0=x;
rs=0;
rw=0;
en=1;
delay(1);
en=0;
}
在代码的这一部分中,我们将数据发送到16 * 2 LCD显示器。数据将复制到 8051 微控制器的端口 0。RS 设置为高电平以进行命令写入。对于写入操作,RW 设置为低电平。在使能(E)引脚上施加高到低脉冲以启动数据写入操作。
void datawrt (unsigned char y)
{
P0=y;
rs=1;
rw=0;
en=1;
delay(1);
en=0;
}
这就是我们使用8051微控制器测量任何信号频率的方式。
#include
sbit rs=P2^7;
sbit rw=P2^6;
sbit en=P2^5;
void delay(unsigned int) ;
void cmdwrt(unsigned char);
void datawrt(unsigned char);
void main (void)
{
unsigned long int pulses;
unsigned char i;
unsigned int s1,s2,s3,s4;
unsigned char d1,d2,d3,d4,d5,d6;
unsigned char cmd[]={0x38,0x01,0x06,0x0c,0x82};
unsigned char msg[]={"Freq: "};
unsigned char msg2[]={" Hz"};
for(i=0;i<5;i++)
{
cmdwrt(cmd[i]);
delay(1);
}
while(1)
{
TMOD=0x51;
TL1=0;
TH1=0;
TR1=1;
delay(100);
TR1=0;
pulses= TH1*256 + TL1;
pulses=pulses*10;
d1=pulses%10;
s1=pulses%100;
s2=pulses%1000;
s3=pulses%10000;
s4=pulses%100000;
d2=(s1-d1)/10;
d3=(s2-s1)/100;
d4=(s3-s2)/1000;
d5=(s4-s3)/10000;
d6=(pulses-s4)/100000;
cmdwrt(0x01);
delay(1);
for(i=0;msg[i]!='';i++)
datawrt(msg[i]);
if(pulses>=100000)
datawrt(0x30+d6);
if(pulses>=10000)
datawrt(0x30+d5);
if(pulses>=1000)
datawrt(0x30+d4);
if(pulses>=100)
datawrt(0x30+d3);
if(pulses>=10)
datawrt(0x30+d2);
datawrt(0x30+d1);
for(i=0;msg2[i]!='';i++)
datawrt(msg2[i]);
delay(1000);
}
}
void cmdwrt (unsigned char x)
{
P0=x;
rs=0;
rw=0;
en=1;
delay(1);
en=0;
}
void datawrt (unsigned char y)
{
P0=y;
rs=1;
rw=0;
en=1;
delay(1);
en=0;
}
void delay(unsigned int z)
{
unsigned int p;
for(p=0;p