assass123 发表于 2024-12-17 20:02:07

<p>学习这些基本的C语言运算和输出后,简单的小程序应该可以试验一下。</p>

assass123 发表于 2024-12-17 20:43:32

<p>打卡Ai8051U视频教程第六集-IO输入输出</p>
<p>GPIO(General Purpose I/O Ports)意思为通用输入/输出端口,通俗地说,就是一些引脚,可以通过它们输出高低电平或者通过它们读入引脚的状态-是高电平或是低电平。</p>
<p>GPIO的工作模式<br />
<img src="data/attachment/forum/202412/17/204023we2bwwjfij6dj7cw.png" alt="image.png" title="image.png" /></p>
<p>硬件参数<br />
<img src="data/attachment/forum/202412/17/204058izl3nyih883stmci.png" alt="image.png" title="image.png" /></p>
<p>了解后介绍了一个简单的按键开关软件处理程序</p>
<p><img src="data/attachment/forum/202412/17/204143cg0nqq0g9j45q9zj.png" alt="image.png" title="image.png" /></p>
<p>讲解了处理按键过程抖动处理的方法</p>
<p><img src="data/attachment/forum/202412/17/204304zvqjqlyloot0d7jm.png" alt="image.png" title="image.png" /></p>
<p>延时一下,就好了</p>

assass123 发表于 2024-12-19 18:49:07

<p>打卡Ai8051U视频教程第七集-定时器</p>
<p><img src="data/attachment/forum/202412/19/184306mwd059gdfvgrgkrv.png" alt="image.png" title="image.png" /></p>
<p>应用方便的定时器计算器</p>
<p>讲解透彻的定时器寄存器设置</p>
<p><img src="data/attachment/forum/202412/19/184416p311eah9q5bu8qaw.png" alt="image.png" title="image.png" />定时器计算公式</p>
<p><img src="data/attachment/forum/202412/19/184526wvqgzj2wcgh4jbri.png" alt="image.png" title="image.png" /></p>
<p>从原理、公式、寄存器设置,完整、形象</p>
<p>还介绍了函数体大编写和调用</p>
<p><img src="data/attachment/forum/202412/19/184700s2wpqqpz3mmz3psp.png" alt="image.png" title="image.png" /></p>
<p><img src="data/attachment/forum/202412/19/184736aaw3auuahs7m7aum.png" alt="image.png" title="image.png" /></p>
<p>以及简单的救护车闪烁程序</p>
<p>#include &quot;ai8051u.h&quot;                        //调用头文件<br />
#include &quot;stc32_stc8_usb.h&quot;                //调用头文件<br />
#include &quot;intrins.h&quot;                        //d调用头文件</p>
<p>#define u8unsigned char                //8位无符号变量(0-255)<br />
#define u16 unsigned int                //16位无符号变量(0-65535)</p>
<p>u8 state = 0;                                        //初始状态<br />
u8 Run_State = 0;                                //运行状态</p>
<p>char *USER_DEVICEDESC = NULL;<br />
char *USER_PRODUCTDESC = NULL;<br />
char *USER_STCISPCMD = &quot;@STCISP#&quot;;</p>
<p>void Delay20ms(void)        //@24.000MHzDelay20ms();<br />
{<br />
unsigned long edata i;</p>
<pre><code>_nop_();
_nop_();
i = 119998UL;
while (i) i--;
</code></pre>
<p>}<br />
void Timer0_Init(void);                //3秒@24.000MHz                //函数声明</p>
<p>void main(void)<br />
{<br />
int count=1;                                                                        //按键计数变量</p>
<pre><code>WTST = 0;                                                                                //设置程序指令延时参数,赋值为0可将CPU执行指令的速度设置为最快
EAXFR = 1;                                                                                 //扩展寄存器(XFR)访问使能
CKCON = 0;                                                                                 //提高访问XRAM速度

P0M1 = 0x00;   P0M0 = 0x00;
P1M1 = 0x00;   P1M0 = 0x00;
P2M1 = 0x00;   P2M0 = 0x00;
P3M1 = 0x00;   P3M0 = 0x00;
P4M1 = 0x00;   P4M0 = 0x00;
P5M1 = 0x00;   P5M0 = 0x00;
P6M1 = 0x00;   P6M0 = 0x00;
P7M1 = 0x00;   P7M0 = 0x00;

usb_init();                                     //USB CDC 接口配置

IE2 |= 0x80;                                    //使能USB中断
</code></pre>
<p>//        Timer0_Init();                                                                        //定时器初始化</p>
<pre><code>EA = 1;                                                                                        //IE |= 0X80;

P40 = 0;

while (DeviceState != DEVSTATE_CONFIGURED);   //等待USB完成配置

while(1)
{

    if (bUsbOutReady)                                                        //如果接收到了数据
    {
      //USB_SendData(UsbOutBuffer,OutNumber);   //发送数据缓冲区,长度(接收数据原样返回, 用于测试)
      
      usb_OUT_done();                                                        //
    }

</code></pre>
<p>//                //任务1:<br />
//                if( P32 == 0 )                                                                //判断P32按钮是否按下<br />
//                {<br />
//                        Delay20ms();                                                        //延时20ms消抖<br />
//                        if( P32 == 0 )<br />
//                        {<br />
//                                printf(&quot;按键按下次数\xfd:%d 次\r\n&quot;,(int)count);<br />
//                                count++;<br />
//                        <br />
//                                while( P32 == 0 );                                        //等待P32松开<br />
//                        <br />
//                        }<br />
//                }</p>
<p>//                //任务2:灯按一下点亮三秒后熄灭。<br />
//                if( P32 == 0 )                                                                //判断P32按钮是否按下<br />
//                {<br />
//                        Delay20ms();                                                        //延时20ms消抖<br />
//                        if( P32 == 0 )<br />
//                        {<br />
////                                printf(&quot;按键按下次数\xfd:%d 次\r\n&quot;,(int)count);<br />
////                                count++;<br />
//                                P00 = 0;<br />
//                                Timer0_Init();<br />
//                                while( P32 == 0 );                                        //等待P32松开<br />
//                        <br />
//                        }<br />
//                }</p>
<p>//        <br />
//任务3:救护车灯控制器,按下报警按钮,红蓝交替闪烁(LED1和LED2              表示红和蓝灯),再按一下报警按钮,红蓝灯停止。<br />
if( P32 == 0 )                                                                //判断P32按钮是否按下<br />
{<br />
Delay20ms();                                                        //延时20ms消抖<br />
if( P32 == 0 )<br />
{<br />
Run_State = !Run_State;                                //运行状态取反</p>
<pre><code>                        if( Run_State==1 )                                        //运行
                        {
                                Timer0_Init();
                        }
                        else
                        {
                                TR0 = 0;                                                //关闭定时器
                                P00 = 1;
                                P01 = 1;
                        }
</code></pre>
<p>//                                P00 = 0;<br />
//                                Timer0_Init();<br />
while( P32 == 0 );                                        //等待P32松开</p>
<pre><code>                }
        }

}
</code></pre>
<p>}</p>
<p>//void Timer0_Init(void)                //3秒@24.000MHz        函数定义<br />
//{<br />
//        TM0PS = 0x5B;                        //设置定时器时钟预分频 ( 注意:并非所有系列都有此寄存器,详情请查看数据手册 )<br />
//        AUXR &amp;= 0x7F;                        //定时器时钟12T模式<br />
//        TMOD &amp;= 0xF0;                        //设置定时器模式<br />
//        TL0 = 0x3F;                                //设置定时初始值<br />
//        TH0 = 0x01;                                //设置定时初始值<br />
//        TF0 = 0;                                //清除TF0标志<br />
//        TR0 = 1;                                //定时器0开始计时<br />
//        ET0 = 1;                                //使能定时器0中断<br />
//<br />
//        //TM0PS = 91<br />
//        //12T                 /12<br />
//        // THO-TL0 = 319<br />
//<br />
//}</p>
<p>void Timer0_Init(void)                //500毫秒@24.000MHz<br />
{<br />
TM0PS = 0x0F;                        //设置定时器时钟预分频 ( 注意:并非所有系列都有此寄存器,详情请查看数据手册 )<br />
AUXR &amp;= 0x7F;                        //定时器时钟12T模式<br />
TMOD &amp;= 0xF0;                        //设置定时器模式<br />
TL0 = 0xDC;                                //设置定时初始值<br />
TH0 = 0x0B;                                //设置定时初始值<br />
TF0 = 0;                                //清除TF0标志<br />
TR0 = 1;                                //定时器0开始计时<br />
ET0 = 1;                                //使能定时器0中断<br />
}</p>
<p>void Timer0_Isr(void) interrupt 1                //3秒执行一次<br />
{<br />
state = !state;</p>
<pre><code>P00 = state;
P01 = !state;
</code></pre>
<p>}</p>

assass123 发表于 2024-12-19 20:08:55

<p>打卡Ai8051U视频教程第八集-定时器周期性调度任务</p>
<p><img src="data/attachment/forum/202412/19/194105uoto4aao94otfid4.png" alt="image.png" title="image.png" /></p>
<p>基于1MS的时钟中断</p>
<p>void Timer0_Isr(void) interrupt 1                //1MS执行一次<br />
{</p>
<pre><code>Task_Marks_Handler_Callback();                                        //系统计时
</code></pre>
<p>}</p>
<p>如何建造.C 和.H文件</p>
<p><img src="data/attachment/forum/202412/19/200225n3s4y1n1n1ycsjoo.png" alt="image.png" title="image.png" /></p>
<p>首先,是CONFIG.H头文件</p>
<p>#ifndef __CONFIG_H<br />
#define __CONFIG_H</p>
<p>#include &quot;ai8051u.h&quot;                        //调用头文件<br />
#include &quot;stc32_stc8_usb.h&quot;                //调用头文件<br />
#include &quot;intrins.h&quot;                        //d调用头文件</p>
<p>#define u8unsigned char                //8位无符号变量(0-255)<br />
#define u16 unsigned int                //16位无符号变量(0-65535)</p>
<p>void Sys_init(void);                        //函数声明<br />
void Timer0_Init(void);                 //1毫秒@24.000MHz</p>
<p>#endif</p>
<p>接着设置输出端口方式,和定时器1MS</p>
<p>#include &quot;config.h&quot;</p>
<p>void Sys_init(void)<br />
{<br />
WTST = 0;                                                                                //设置程序指令延时参数,赋值为0可将CPU执行指令的速度设置为最快<br />
EAXFR = 1;                                                                                 //扩展寄存器(XFR)访问使能<br />
CKCON = 0;                                                                                 //提高访问XRAM速度</p>
<pre><code>P0M1 = 0x00;   P0M0 = 0x00;
P1M1 = 0x00;   P1M0 = 0x00;
P2M1 = 0x00;   P2M0 = 0x00;
P3M1 = 0x00;   P3M0 = 0x00;
P4M1 = 0x00;   P4M0 = 0x00;
P5M1 = 0x00;   P5M0 = 0x00;
P6M1 = 0x00;   P6M0 = 0x00;
P7M1 = 0x00;   P7M0 = 0x00;
</code></pre>
<p>}</p>
<p>void Timer0_Init(void)                //1毫秒@24.000MHz<br />
{<br />
TM0PS = 0x00;                        //设置定时器时钟预分频 ( 注意:并非所有系列都有此寄存器,详情请查看数据手册 )<br />
AUXR &amp;= 0x7F;                        //定时器时钟12T模式<br />
TMOD &amp;= 0xF0;                        //设置定时器模式<br />
TL0 = 0x30;                                //设置定时初始值<br />
TH0 = 0xF8;                                //设置定时初始值<br />
TF0 = 0;                                //清除TF0标志<br />
TR0 = 1;                                //定时器0开始计时<br />
ET0 = 1;                                //使能定时器0中断<br />
}</p>
<p>再就是设置IO口功能</p>
<p>头文件</p>
<p>#ifndef __IO_H<br />
#define __IO_H</p>
<p>#include &quot;config.h&quot;                        //调用头文件</p>
<p>void LED0_Blink(void);<br />
void LED1_Blink(void);<br />
void LED2_Blink(void);</p>
<p>void KEY_Task(void);</p>
<p>#endif</p>
<p>设置IO状态</p>
<p>#include &quot;io.h&quot;</p>
<p>u8 State1 = 0;                                        //LED1初始状态<br />
u8 State2 = 0;                                        //LED2初始状态<br />
u8 State3 = 0;                                        //LED3初始状态</p>
<p>u16 Key_Vol = 0;                                //按键按下持续时间</p>
<p>void LED0_Blink(void)<br />
{<br />
State1 = !State1;<br />
P00 = State1;<br />
}</p>
<p>void LED1_Blink(void)<br />
{<br />
State2 = !State2;<br />
P01 = State2;<br />
}</p>
<p>void LED2_Blink(void)<br />
{<br />
State3 = !State3;<br />
P02 = State3;<br />
}</p>
<p>void KEY_Task(void)<br />
{<br />
if( P32 == 0 )<br />
{<br />
Key_Vol++;<br />
if( Key_Vol==5 )<br />
{<br />
//按键按下的任务<br />
printf( &quot;按键单击\r\n&quot; );<br />
}<br />
}<br />
else<br />
{<br />
Key_Vol = 0;<br />
}</p>
<p>}</p>
<p>task.h头文件</p>
<p>#ifndef __TASK_H<br />
#define __TASK_H</p>
<p>#include &quot;config.h&quot;                        //调用头文件</p>
<p>typedef struct<br />
{<br />
u8 Run;               //任务状态:Run/Stop<br />
u16 TIMCount;         //定时计数器<br />
u16 TRITime;          //重载计数器<br />
void (*TaskHook) (void); //任务函数<br />
} TASK_COMPONENTS;</p>
<p>void Task_Marks_Handler_Callback(void);<br />
void Task_Pro_Handler_Callback(void);</p>
<p>#endif</p>
<p>扫描结构和数组,实现</p>
<p>task.c程序</p>
<p>#include &quot;task.h&quot;<br />
#include &quot;io.h&quot;</p>
<p>static TASK_COMPONENTS Task_Comps[]=<br />
{<br />
//状态计数周期函数</p>
<p>{0, 300,   300,   LED0_Blink},      /* task 1 Period: 300ms <em>/<br />
{0, 600,   600,   LED1_Blink},      /</em> task 1 Period: 600ms <em>/<br />
{0, 900,   900,   LED2_Blink},      /</em> task 1 Period: 600ms <em>/<br />
{0, 10,    10,    KEY_Task},      /</em> task 1 Period: 600ms */<br />
};</p>
<p>u8 Tasks_Max = sizeof(Task_Comps)/sizeof(Task_Comps);</p>
<p>//========================================================================<br />
// 函数: Task_Handler_Callback<br />
// 描述: 任务标记回调函数.<br />
// 参数: None.<br />
// 返回: None.<br />
// 版本: V1.0, 2012-10-22<br />
//========================================================================<br />
void Task_Marks_Handler_Callback(void)<br />
{<br />
u8 i;<br />
for(i=0; i&lt;Tasks_Max; i++)<br />
{<br />
if(Task_Comps.TIMCount)      /* If the time is not 0 <em>/<br />
{<br />
Task_Comps.TIMCount--;   /</em> Time counter decrement <em>/<br />
if(Task_Comps.TIMCount == 0) /</em> If time arrives */<br />
{<br />
/*Resume the timer value and try again <em>/<br />
Task_Comps.TIMCount = Task_Comps.TRITime;<br />
Task_Comps.Run = 1;      /</em> The task can be run */<br />
}<br />
}<br />
}<br />
}</p>
<p>//========================================================================<br />
// 函数: Task_Pro_Handler_Callback<br />
// 描述: 任务处理回调函数.<br />
// 参数: None.<br />
// 返回: None.<br />
// 版本: V1.0, 2012-10-22<br />
//========================================================================<br />
void Task_Pro_Handler_Callback(void)<br />
{<br />
u8 i;<br />
for(i=0; i&lt;Tasks_Max; i++)<br />
{<br />
if(Task_Comps.Run) /* If task can be run <em>/<br />
{<br />
Task_Comps.Run = 0;      /</em> Flag clear 0 <em>/<br />
Task_Comps.TaskHook();   /</em> Run task */<br />
}<br />
}<br />
}</p>
<p>都准备好了,开始主程序</p>
<p>#include &quot;config.h&quot;<br />
#include &quot;task.h&quot;<br />
#include &quot;io.h&quot;</p>
<p>char *USER_DEVICEDESC = NULL;<br />
char *USER_PRODUCTDESC = NULL;<br />
char *USER_STCISPCMD = &quot;@STCISP#&quot;;</p>
<p>void main(void)<br />
{<br />
Sys_init();                                                                                //系统初始化<br />
usb_init();                                     //USB CDC 接口配置</p>
<pre><code>IE2 |= 0x80;                                    //使能USB中断
Timer0_Init();                                                                        //定时器初始化
EA = 1;                                                                                        //IE |= 0X80;

P40 = 0;

while (DeviceState != DEVSTATE_CONFIGURED);   //等待USB完成配置

while(1)
{

    if (bUsbOutReady)                                                        //如果接收到了数据
    {
      //USB_SendData(UsbOutBuffer,OutNumber);   //发送数据缓冲区,长度(接收数据原样返回, 用于测试)
       
      usb_OUT_done();                                                        //
    }
        Task_Pro_Handler_Callback();                                //执行功能函数

}
</code></pre>
<p>}</p>
<p>void Timer0_Isr(void) interrupt 1                //1MS执行一次<br />
{</p>
<pre><code>Task_Marks_Handler_Callback();                                        //系统计时
</code></pre>
<p>}</p>

assass123 发表于 2024-12-19 20:09:24

<p>打卡前八集完成</p>

assass123 发表于 2024-12-19 20:12:29

<p>第八集的结构1MS扫描累加,模拟并行多任务设计了不错</p>

assass123 发表于 2025-1-7 19:26:32

收到了厂家的Ai8051U试验箱   试验箱非常漂亮

assass123 发表于 2025-1-7 19:27:38

数据线质量也很好

assass123 发表于 2025-1-7 19:28:19

PCB做工很好

assass123 发表于 2025-1-7 19:29:31

马上上电,电子表运转稳定
页: 1 [2]
查看完整版本: 学习Ai8051U视频打卡