Declare a work queue suspend_work_queue in wakelock. C.
Struct workqueue_struct * suspend_work_queue;
Then create it. This work queue is the core of earlysuspend.
Suspend_work_queue = create_singlethread_workqueue ("Suspend ");
In earlysuspend. C, we declare two jobs: early_suspend_work and late_resume_work,
Static declare_work (early_suspend_work, early_suspend );
Static declare_work (late_resume_work, late_resume );
Then, in the request_suspend_state function, insert them into the above work queue based on the previous power status and Request status.
If (! Old_sleep & new_state! = Pm_suspend_on ){
State | = suspend_requested;
Queue_work (suspend_work_queue, & early_suspend_work );
} Else if (old_sleep & new_state = pm_suspend_on ){
State & = ~ Suspend_requested;
Wake_lock (& main_wake_lock );
Queue_work (suspend_work_queue, & late_resume_work );
}
After being inserted to the work queue, the Task Force column will schedule the execution, that is, the early_suspend or late_resume function will be executed.
List_for_each_entry (Pos, & early_suspend_handlers, link ){
If (POS-> suspend! = NULL ){
If (debug_mask & debug_verbose)
Pr_info ("early_suspend: Calling % pf \ n", pos-> suspend );
Pos-> suspend (POS );
}
}
In the early_suspend function, the early_suspend_handlers linked list is used. At the beginning of earlysuspend. C, A Global static early_suspend_handlers linked list is declared.
Static list_head (early_suspend_handlers );