YangHY 发表于 2026-1-29 13:20:13

中断接受:

void Uart2_Isr(void) interrupt 8
{
        if (S2CON & 0x02)        //检测串口2发送中断
        {
                S2CON &= ~0x02;        //清除串口2发送中断请求位
                B_TX2_Busy = 0;
        }
        if (S2CON & 0x01)        //检测串口2接收中断
        {
                S2CON &= ~0x01;        //清除串口2接收中断请求位
               
                UR2TOCR = 0xe0;//开启超时中断,使用系统时钟

                //S2BUF
                Rec_Dat = S2BUF;
        }
       
    if(UR2TOSR & 0x01)   //串口超时中断
    {
      B_RX2_OK = 1;      //接收完成标志位
      UR2TOSR = 0x00;    //清除超时标志位
      UR2TOCR = 0x00;    //关闭超时中断
    }
}

YangHY 发表于 2026-1-29 14:01:08

这个函数只运行4ms,任务调度要点时间,1ms才执行1次
但他这个总共延时也就三点几毫秒,所以要直接在主函数里面调用:

void main(void)
{
        Sys_init();                                                                                //系统初始化
        usb_init();                                     //USB CDC 接口配置

    IE2 |= 0x80;                                    //使能USB中断
        Timer0_Init();                                                                        //定时器初始化
//        Init_595();
//        INT1_Init();                                                                        //外部中断1初始化
//        P3_IO_Init();                                                                        //IO中断初始化
//        P4_IO_Init();
       
        //TIM1_Count_Init();
        Timer1_Init();
        Uart2_Init();                                                                        //串口2初始化
       
    EA = 1;                                                                                        //IE |= 0X80;
       
        P40 = 0;
       
        while (DeviceState != DEVSTATE_CONFIGURED);   //等待USB完成配置
//        WDT_CONTR = 0X24;
       
        while(1)
        {
               
                Usart2_RunTask();//这个函数只运行4ms,任务调度要点时间,1ms才执行1次
                //但他这个总共延时也就三点几毫秒,所以要直接在主函数里面调用
               
      if (bUsbOutReady)                                                        //如果接收到了数据
      {
            //USB_SendData(UsbOutBuffer,OutNumber);   //发送数据缓冲区,长度(接收数据原样返回, 用于测试)
                       
            usb_OUT_done();                                                        //
      }
//                Task_Pro_Handler_Callback();                                //执行功能函数
               


        }
}

YangHY 发表于 2026-1-29 14:03:24

课后练习:



今天的第18课就到此结束

YangHY 发表于 2026-1-30 19:25:49

今天我们补回第十五集 定时器做计数器

今天重点学习计数器的用法:

YangHY 发表于 2026-1-30 19:28:15

实际就是带有高低电平变化的传感器的,

都要用到计数器:

YangHY 发表于 2026-1-30 19:31:45

只要输出信号是高低电平变化的传感器,想要计算个数的就可以用计数器的功能。

这个是纯硬件的,例如1秒输出5000次,人工就没法啦:

高低电平输出的脉冲传感器,我们看看用法:

YangHY 发表于 2026-1-30 19:34:38

看T0 和T1的2个外部引脚:


HMAPS6/I2SSD/MOSI_4/TICLED/TO/P3.411
I2SWS/PVMFLT/SS_4/TOCLKO/T1/P3.512

YangHY 发表于 2026-1-30 19:36:19

TMOD配置:

YangHY 发表于 2026-1-30 19:38:42

中断请求标志位:

YangHY 发表于 2026-1-30 19:42:49

任务1:编写定时器1计数的的程序
(为了方便计数,10个脉冲中断一次)
定时器1的计数功能,在STC的模拟万能ISP数码管显示
按P35就可以看到数码管在显示按键次数了

今天我们新建2个文件time.c 和time.h

#include "tim.h"


u32 Count_T1 = 0;

void TIM1_Count_Init(void)
{
        T1_CT = 1;                        //设置为外部计数
        T1_M1 = 0;                        //设置为16位自动重载
        T1_M0 = 0;
        T1_GATE = 0;
       
        TH1 = (65536-Count_num)>>8;        //65526
        TL1 = (65536-Count_num);
       
        P3PU |= 0x20; //用ISP配置P35,打开内置的上拉电阻
                                  //这样就保证P35在没有输入的情况下是高电平
        TR1 = 1;                        //启动定时器1
        ET1 = 1;                        //打开定时器1外部中断
       
}

页: 80 81 82 83 84 85 86 87 88 89 [90] 91 92 93 94 95 96 97 98 99
查看完整版本: 第一课 序言《AI8051U的特点》