[uCOS/RTOS] RTOS 电源管理设计

[复制链接]
1668|7
 楼主| leihen0525 发表于 2018-8-22 10:46 | 显示全部楼层 |阅读模式
讨论一个问题,小弟从事汽车电子行业多年,最近手头项目上了我历时几个月写的实时操作系统,考虑是电动车项目,功耗必然是个大问题,在OS设计之初的时候并没有把电源管理当回事,结果电源管理部分很难和OS完美融合,参考目前众多RTOS的电源管理,似乎这一块设计都很薄弱,感觉并没有把嵌入式的低功耗问题考虑进去,不知道大家对这一块有没有什么好的思路推荐。
先用我手头这个上了系统的项目举个例子:
平台是KEA128 ARM M0+内核的芯片,
按照M0内核的功耗有三种 RUN WIAT STOP
我OS启动会创建一个空闲任务,空闲任务默认进入WAIT
开一个超时定时器 留有一个给任务的API可以重设定时器时间
当定时器时间到 设计空闲任务进入就直接进入STOP 并且开启RTC定时唤醒系统
问题吧 就在这 RTC唤醒后重置定时器时间并且设置空闲进入WAIT 我只是期望唤醒后只执行一些唤醒事件检查任务 但是吧 起初设计系统没有考虑电源管理框架和任务调度的问题 当唤醒后 自然就所有任务都跑起来了
不知道大家有没有这方面经验 比如在睡眠模式下冻结部分任务?
 楼主| leihen0525 发表于 2018-8-22 10:51 | 显示全部楼层
按照汽车上 KL15 IGN作为唤醒和睡眠的信号 我将这个信号设计为 主动睡眠
而我想 要OS具备一个合适的自动睡眠策略 可以根据任务的需求 来动态的降低功耗
已经困扰快一个星期了 不知道 有没有对操作系统 电源管理特别有见解的人 讨论一下这个问题
airwill 发表于 2018-8-27 07:00 | 显示全部楼层
你首先得理清楚,  那些需要休眠, 什么条件休眠.
本身休眠的问题不算是 RTOS 内核要管理解决的问题.

什么 RTOS, M0 应该跑不了太复杂的 OS.
caijie001 发表于 2018-8-27 13:39 | 显示全部楼层
用os就别要低功耗吧,,,,os是为了快速响应跟线程管理的。低功耗那些裸机就好了呗
 楼主| leihen0525 发表于 2018-8-28 14:26 | 显示全部楼层
airwill 发表于 2018-8-27 07:00
你首先得理清楚,  那些需要休眠, 什么条件休眠.
本身休眠的问题不算是 RTOS 内核要管理解决的问题.

我可能是受到Windows系统的影响
不过好在理清楚一些问题
OS还是要跑起来的
我设计的初衷是想让OS做更多的事情 task可以减少设计复杂度
 楼主| leihen0525 发表于 2018-8-28 14:29 | 显示全部楼层
caijie001 发表于 2018-8-27 13:39
用os就别要低功耗吧,,,,os是为了快速响应跟线程管理的。低功耗那些裸机就好了呗 ...

低功耗吧 在车上 点火开了 一般就不考虑功耗 至少目前汽车电子 是这样的
只有点火关了 功耗要求还是很高的 毕竟长时间蓄电池会亏电
毕竟现在单片机很强 嵌入式跑OS很正常 当然嵌入式功耗电源还是很重要的 不是么
 楼主| leihen0525 发表于 2018-8-28 14:39 | 显示全部楼层
  1. void Power_Idle_Task(void* pdata)
  2. {
  3.         UART_Init();
  4.         Uart_SendChar(0xEF);
  5.         Power_Init();


  6.         Timer_Init();//定时器初始化

  7.         //System_Debug_Init();

  8.         Services_Init();//服务组件

  9.         Application_Init();//应用程序


  10.         while(1)
  11.         {
  12.                 //喂狗
  13.                 API_User_WDOG_Refresh();

  14.                 switch (Power.Power_Status)
  15.                 {
  16.                         //1.设置进入Stop时间为1S
  17.                         //2.设置当前进入模式为wait模式
  18.                         case Power_Status_Init:
  19.                         {
  20.                                 Power_RTC_SET_Time_User(1000,false);
  21.                                 API_User_SOC_Enter_Wait_Mode();

  22.                                 Power.Power_Status=Power_Status_Runing;
  23.                         }break;

  24.                         //1.设置当前在wait模式下运行时间为20MS
  25.                         //2.设置当前进入模式为wait模式
  26.                         //3.开启任务调度系统
  27.                         case Power_Status_Enter_Wait:
  28.                         {
  29.                                 Power_RTC_SET_Time_User(20,false);

  30.                                 API_User_SOC_Enter_Wait_Mode();
  31.                                 API_User_OS_Resume();

  32.                                 Power.Power_Status=Power_Status_Runing;

  33.                         }// @suppress("No break at end of case")

  34.                         //进入低功耗模式
  35.                         case Power_Status_Runing:
  36.                         {
  37.                                 asm("wfi");

  38.                         }break;

  39.                         //1.关闭任务调度系统
  40.                         //2.设置当前进入低功耗模式
  41.                         //3.设置唤醒stop模式时间为1S
  42.                         case Power_Status_Enter_Stop:
  43.                         {
  44.                                 API_User_OS_Suspend();
  45.                                 API_User_SOC_Enter_Stop_Mode();
  46.                                 Power_RTC_SET_Time_User(1000,false);

  47.                                 Power.Power_Status=Power_Status_Stoping;
  48.                         }// @suppress("No break at end of case")

  49.                         //进入低功耗模式
  50.                         case Power_Status_Stoping:
  51.                         {
  52.                                 asm("wfi");
  53.                         }// @suppress("No break at end of case")

  54.                         //1.检查当前唤醒信号是否有效
  55.                         //2.如果唤醒信号有效则进入wait模式
  56.                         case Power_Status_Check_WakeUp_Signal:
  57.                         {
  58.                                 Function_Groups_Run(&Power.FGN,Null,Power_Check_WakUp);
  59.                         }break;

  60.                         default:
  61.                         {

  62.                         }break;
  63.                 }


  64.         }

  65. }
  1. static void Services_Sleep_Task(void *pdata)
  2. {

  3.         Services_Input_Link_Event_Flag_Group();


  4.         while(1)
  5.         {
  6.                 switch (Services_Sleep.Status)
  7.                 {
  8.                         case Services_Sleep_Status_Init:
  9.                         {
  10.                                 Function_Groups_Init(&Services_Sleep.Operation_Function);
  11.                                 Services_Sleep.Status=Services_Sleep_Status_Enter_WakeUp;
  12.                                 API_User_Wait_Enter_Stop_Times(1000,true);
  13.                                 API_User_Sleep(50);
  14.                         }break;

  15.                         case Services_Sleep_Status_Runing:
  16.                         {

  17.                                 Event_Return_Type ER=Services_Input_Wait_Status(SI_IGN_IN,IO_OFF,100);
  18.                                 if(ER==Event_Return_OK)
  19.                                 {
  20.                                         API_User_Wait_Enter_Stop_Times(1000,true);

  21.                                         API_User_Sleep(500);

  22.                                         if(Services_Input_GET_Status(SI_IGN_IN)==IO_OFF)
  23.                                         {
  24.                                                 Services_Sleep.Status=Services_Sleep_Status_Enter_Sleep;
  25.                                                 API_User_Wait_Enter_Stop_Times(1000,true);
  26.                                         }
  27.                                         else
  28.                                         {
  29.                                                 ;
  30.                                         }
  31.                                 }
  32.                                 else if(ER==Event_Return_Time_Out)
  33.                                 {
  34.                                         API_User_Wait_Enter_Stop_Times(1000,true);
  35.                                 }
  36.                                 else
  37.                                 {
  38.                                         API_User_Sleep(100);
  39.                                 }
  40.                         }break;
  41.                         case Services_Sleep_Status_DeepSleep:
  42.                         {
  43.                                 if(Services_Input_Wait_Status(SI_IGN_IN,IO_ON,-1)==Event_Return_OK)
  44.                                 {
  45.                                         Services_Sleep.Status=Services_Sleep_Status_Enter_WakeUp;
  46.                                 }
  47.                         }break;

  48.                         case Services_Sleep_Status_Enter_WakeUp:
  49.                         {
  50.                                 API_User_Wait_Enter_Stop_Times(1000,true);

  51.                                 Function_Groups_Run(&Services_Sleep.Operation_Function,(void *)Services_Sleep_Operation_Enter_WakeUp,Null);
  52.                                 //API_User_Timer_WakeUp();
  53.                                 Services_Sleep.Status=Services_Sleep_Status_Runing;


  54.                         }break;
  55.                         case Services_Sleep_Status_Enter_Sleep:
  56.                         {
  57.                                 Function_Groups_Run(&Services_Sleep.Operation_Function,(void *)Services_Sleep_Operation_Enter_Sleep,Null);
  58.                                 //API_User_Timer_Sleep();
  59.                                 Services_Sleep.Status=Services_Sleep_Status_DeepSleep;
  60.                         }break;

  61.                         default:
  62.                         {
  63.                                 API_User_Sleep(100);
  64.                         }break;
  65.                 }

  66.         }
  67. }

既然没有朋友有实质性结果 我就把思路贴出来吧 上面两个任务 第一个是系统空闲任务 优先级最低 属于内核任务 第二个是服务类任务 因为我的内核设计是微内核架构 第二个服务是检查IGN主动睡眠 第一个是 OS自动根据任务需求睡眠 唤醒 运行等需求 整体在睡眠下功耗做到了0.5MA 低于客户要求的1MA 有需要的小伙伴们可以了解一下
caijie001 发表于 2018-8-28 18:37 | 显示全部楼层
leihen0525 发表于 2018-8-28 14:29
低功耗吧 在车上 点火开了 一般就不考虑功耗 至少目前汽车电子 是这样的
只有点火关了 功耗要求还是很高 ...

你也可以这样理解,反正看情况需要吧,嵌入式这个东西就是可裁剪的,专向设备
您需要登录后才可以回帖 登录 | 注册

本版积分规则

13

主题

55

帖子

3

粉丝
快速回复 在线客服 返回列表 返回顶部