DIY编程器网

 找回密码
 注册

QQ登录

只需一步,快速开始

扫一扫,访问微社区

查看: 189|回复: 0
打印 上一主题 下一主题

混合式调度器C51源代码

[复制链接]
跳转到指定楼层
楼主
发表于 2012-1-18 00:59:36 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
/*==============================================================
1ms时标 混合式调度器(一个抢占式任务,多个合作式任务)
作者:shadow.hu
===============================================================*/
#include
#define uchar  unsigned char
#define ushort unsigned short
#define SCH_MAX_TASKS 9
#define ERROR_SCH_TOO_MANY_TASKS  9
#define ERROR_SCH_CANOT_DELETE_TASK 0
#define RETURN_ERROR 0
#define RETURN_NORMAL 1

#define INTERRPT_Timer_2_Overflow 5

#define SCH_REPORT_ERRORS
#ifdef  SCH_REPORT_ERRORS
#define Error_Port P1
#endif

typedef data struct
{
    void (code *pTask)(void);
ushort Delay;
ushort Period;
ushort RunMe;
uchar  Co_op;//如果任务是合作式的,设置为1,如果任务是抢占式的,设置为0
}sTask;
sTask SCH_tasks_G[SCH_MAX_TASKS];

void SCH_Init_T2(void);
uchar SCH_Add_Task(void (code * pFunction)(),const ushort Delay,   ushort PERIOD);
//                      函数名指针                 延时的时标数    执行任务的时间间隔
//                                                 为0则立即执行   如果为0,表示单次任务   
void SCH_Dispatch_Tasks(void);
void SCH_Start(void);
bit SCH_Delete_Task(const ushort TASK_INDEX);
void SCH_Go_To_Sleep(void);
void SCH_Report_Status(void);//报告系统状况
void LED_Flash_Init(void);
void LED_Flash_Update_A(void);
void LED_Flash_Update_B(void);
void LED_Flash_Update_C(void);
void LED_Flash_Update_D(void);
void LED_Flash_Update_E(void);
void LED_Flash_Update_F(void);
void LED_Flash_Update_G(void);
void LED_Flash_Update_H(void);

uchar Error_code_G = 0;//
static ushort Error_tick_count_G;//记住自从上一次纪录错误以来的时间
static uchar Last_error_code_G;//上次的错误代码(在1分钟之后复位)

uchar  LED_State_G_A = 0;
uchar  LED_State_G_B = 0;
uchar  LED_State_G_C = 0;
uchar  LED_State_G_D = 0;
uchar  LED_State_G_E = 0;
uchar  LED_State_G_F = 0;
uchar  LED_State_G_G = 0;
uchar  LED_State_G_H = 0;

sbit LED_pin_A = P1^0;
sbit LED_pin_B = P1^1;
sbit LED_pin_C = P1^2;
sbit LED_pin_D = P1^3;
sbit LED_pin_E = P1^4;
sbit LED_pin_F = P1^5;
sbit LED_pin_G = P1^6;
sbit LED_pin_H = P1^7;

//Error_code_G = ERROR_SCH_TOO_MANY_TASKS;
//Error_code_G = ERROR_SCH_WAITING_FOR_SLAVE_TO_ACK;
//Error_code_G = ERROR_SCH_WAITING_FOR_START_COMAND_FROM_MASTER;
//Error_code_G = ERROR_SCH_ONE_OR_MORE_SLAVES_DID_NOT_START;
//Error_code_G = ERROR_SCH_LOST_SLAVE;
//Error_code_G = ERROR_SCH_CAN_BUS_ERROR;
//Error_code_G = ERROR_I2C_WRITE_BYTE_AT24C64;

void main(void)
{
SCH_Init_T2();
LED_Flash_Init();
SCH_Add_Task(LED_Flash_Update_A,0,1000);//添加一个任务
SCH_Add_Task(LED_Flash_Update_B,0,2000);//添加一个任务
SCH_Add_Task(LED_Flash_Update_C,0,3000);//添加一个任务
SCH_Add_Task(LED_Flash_Update_D,0,4000);//添加一个任务
SCH_Add_Task(LED_Flash_Update_E,0,5000);//添加一个任务
SCH_Add_Task(LED_Flash_Update_F,0,6000);//添加一个任务
SCH_Add_Task(LED_Flash_Update_G,0,7000);//添加一个任务
SCH_Add_Task(LED_Flash_Update_H,0,8000);//添加一个任务
SCH_Start();//开全局中断
while(1)
{
  SCH_Dispatch_Tasks();
}
}
/*------------------------------------------------------------
这是调度器的中断服务程序,初始化函数中的定时器设置决定了它
的调度频率,这个版本的调度器由定时器2触发中断,定时器自动重装。
-------------------------------------------------------------*/
void SCH_Update(void) interrupt INTERRPT_Timer_2_Overflow
{
//刷新任务队列
uchar Index;
TF2 = 0;//必须手工清除
//注意:计算单位为时标(不是毫秒)
for(Index = 0;Index  0)&&(SCH_tasks_G[Index].Co_op))
  {
   (*SCH_tasks_G[Index].pTask)();//执行任务
   SCH_tasks_G[Index].RunMe -= 1;//清除任务需要执行的标志
  }
  //如果这是个“单次”任务,将它从队列中删除
  if(SCH_tasks_G[Index].Period == 0)
  {
   SCH_tasks_G[Index].pTask = 0;// 比通过调用来删除任务更快SCH_Delete_Task(Index);
  }
}
SCH_Report_Status();//报告系统状况
SCH_Go_To_Sleep();
}
void SCH_Start(void)
{
EA = 1;
}
bit SCH_Delete_Task(const ushort TASK_INDEX)
{
bit Return_code;
if(SCH_tasks_G[TASK_INDEX].pTask == 0)
{
  //这里没有任务。。。设置全局错误变量
  Error_code_G = ERROR_SCH_CANOT_DELETE_TASK;
  Return_code = RETURN_ERROR;//返回错误代码
}
else
{
  Return_code = RETURN_NORMAL;
}
//删除任务
SCH_tasks_G[TASK_INDEX].pTask = 0x0000;
SCH_tasks_G[TASK_INDEX].Delay = 0;
SCH_tasks_G[TASK_INDEX].Period = 0;
SCH_tasks_G[TASK_INDEX].RunMe = 0;
return Return_code;
}
void SCH_Go_To_Sleep()
{
PCON |= 0x01;//进入休眠模式
}
void SCH_Report_Status(void)
{
/* #ifdef SCH_REPORT_ERRORS
if(Error_code_G != Last_error_code_G)
{
  Error_Port = 255 - Error_code_G;
  Last_error_code_G = Error_code_G;
  if(Error_code_G != 0)
  {
   Error_tick_count_G = 60000;
  }
  else
  {
   Error_tick_count_G = 0;
  }
}
else
{
  if(Error_tick_count_G != 0)
  {
   if(--Error_count_G == 0)
   {
    Error_code_G = 0;
   }
  }
}
#endif    */
}
void LED_Flash_Update_A(void)
{
if(LED_State_G_A == 1)
{
  LED_State_G_A = 0;
  LED_pin_A = 0;
}
else
{
  LED_State_G_A = 1;
  LED_pin_A = 1;
}
}
void LED_Flash_Update_B(void)
{
if(LED_State_G_B == 1)
{
  LED_State_G_B = 0;
  LED_pin_B = 0;
}
else
                          
                       
                          
                               
{
  LED_State_G_B = 1;
  LED_pin_B = 1;
}
}
void LED_Flash_Update_C(void)
{
if(LED_State_G_C == 1)
{
  LED_State_G_C = 0;
  LED_pin_C = 0;
}
else
{
  LED_State_G_C = 1;
  LED_pin_C = 1;
}
}
void LED_Flash_Update_D(void)
{
if(LED_State_G_D == 1)
{
  LED_State_G_D = 0;
  LED_pin_D = 0;
}
else
{
  LED_State_G_D = 1;
  LED_pin_D = 1;
}
}
void LED_Flash_Update_E(void)
{
if(LED_State_G_E == 1)
{
  LED_State_G_E = 0;
  LED_pin_E = 0;
}
else
{
  LED_State_G_E = 1;
  LED_pin_E = 1;
}
}
void LED_Flash_Update_F(void)
{
if(LED_State_G_F == 1)
{
  LED_State_G_F = 0;
  LED_pin_F = 0;
}
else
{
  LED_State_G_F = 1;
  LED_pin_F = 1;
}
}
void LED_Flash_Update_G(void)
{
if(LED_State_G_G == 1)
{
  LED_State_G_G = 0;
  LED_pin_G = 0;
}
else
{
  LED_State_G_G = 1;
  LED_pin_G = 1;
}
}
void LED_Flash_Update_H(void)
{
if(LED_State_G_H == 1)
{
  LED_State_G_H = 0;
  LED_pin_H = 0;
}
else
{
  LED_State_G_H = 1;
  LED_pin_H = 1;
}
}
void LED_Flash_Init(void)
{
LED_State_G_A= 0;//初始化LED状态
LED_State_G_B= 0;//初始化LED状态
LED_State_G_C= 0;//初始化LED状态
}
                          
                       
                          
                               
分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友 微信微信
收藏收藏 分享分享 支持支持 反对反对
您需要登录后才可以回帖 登录 | 注册

本版积分规则

小黑屋|文字版|手机版|DIY编程器网 ( 桂ICP备14005565号-1 )

GMT+8, 2024-9-28 07:23 , 耗时 0.087497 秒, 18 个查询请求 , Gzip 开启.

各位嘉宾言论仅代表个人观点,非属DIY编程器网立场。

桂公网安备 45031202000115号

DIY编程器群(超员):41210778 DIY编程器

DIY编程器群1(满员):3044634 DIY编程器1

diy编程器群2:551025008 diy编程器群2

QQ:28000622;Email:libyoufer@sina.com

本站由桂林市临桂区技兴电子商务经营部独家赞助。旨在技术交流,请自觉遵守国家法律法规,一旦发现将做封号删号处理。

快速回复 返回顶部 返回列表