int main(void)
{
.................................
{
do
{
sched_run(); // 任务调度,下面更详细说明
if(npa_num_pending_events() > 0) // NPA 事件处理,还没看明白
{
npa_process_event();
}
else
break; // nothing to do--try to sleep
} while(1);
INTLOCK();
if(!npa_num_pending_events() && (sched_get_next_start() >= time_service_now()))
sleep_perform_lpm(); //无任务任理、及NPA事件处理, 系统进入low power mode睡眠模式
INTFREE();
}
}
RPM任务及调度:
rpm_sched.cpp :
Sched &theSchedule()
{
static Sched s;
return s;
}
extern "C" void sched_run()
{
theSchedule().run();
}
void Sched::run()
{
while(true)
{
if(currentTask_)
{
currentTask_->execute(preempt_, stopping_time); // 任务执行 ,所有任务都执行完毕,才返回
}
}
}
void Sched::schedule_task(Task &new_task, ScheduleType schedule_type) // 任务加入到调度list
{
}
rpm_task.cpp
rpm_task.h
class Task
{
public:
// Run this task, completing as much work as it can until the preempt flag becomes nonzero or the task completes.
void execute(volatile bool &preempt, uint64_t stop_time);
protected:
// Overridable function for performing the actual work requested when
// execute() is called. execute() acts as a thin wrapper for this actual
// implmenetation of the function, where the wrapper checks for stop_time
// violations and performs logging, etc.
virtual void execute_until(volatile bool &preempt, uint64_t stop_time) = 0; // virtual function . will achieve in child task class
void schedule_me(ScheduleType schedule_type = DEFAULT); // add itself into sched list
private:
Task *next_task;
Task *prev_task;
bool inImmediateQ_; // task need immediate work list
bool inScheduledQ_; // task sched list
};
{
if(haveDeadline_ && time_service_now() > get_start())
++lateStarts_;
execute_until(preempt, stop_time); // xxxxxxxxxxxxxxx
if(time_service_now() > stop_time)
++lateStops_;
}
void Task::schedule_me(ScheduleType schedule_type)
{
theSchedule().schedule_task (*this, schedule_type); // add itself into sched list
}
class Handler : public Task
{
void enqueue(uint64_t deadline = 0);
protected:
// Prepares, dispatches, and finalizes the request handling.
virtual void execute_until(volatile bool &preempt, uint64_t stop_time);
}
class RBCPRTask : public Task
{
}
class SetChanger : public Task
{
}
uint32 sleep_perform_lpm(void)
{
INTLOCK();
do
{
if(sleep_is_any_interrupt_pending())
{
break;
}
sleep_query_status = npa_query(sleep_uber_query_handle, NPA_QUERY_CURRENT_STATE, &sleep_query_result);
if(0 == (sleep_query_result.data.state & (RPM_VDD_DIG_NEEDED | RPM_VDD_MEM_NEEDED | RPM_CXO_NEEDED)))
{
vdd_min_enter();
vdd_min_exit();
}
else if(0 == (sleep_query_result.data.state & (RPM_CXO_NEEDED)))
{
cxo_shutdown_enter();
cxo_shutdown_exit();
}
else
{
rpm_halt_enter();
rpm_halt_exit();
}
} while(0);
INTFREE();
return 0;
}