当前位置:网站首页>kernel syscore
kernel syscore
2022-07-31 11:52:00 【szembed】
syscore作为低功耗流程的一部分,其涉及的文件主要有syscore_ops.h和syscore.c,这一级别的回调函数是在完全屏蔽中断的场景下进行的。
1、主要结构体struct syscore_ops,该结构体是syscore操作的对象类型。
-
struct
syscore_ops {
-
struct
list_head node;
//用于链表控制,注册和删除syscore对象时操作此链表完成
-
int (*suspend)(
void);
//睡眠流程时回调函数
-
void (*resume)(
void);
//唤醒流程时回调函数
-
void (*shutdown)(
void);
//这一级别的回调函数主要用于系统级的重启、停止或者掉电时才会使用
-
};
2、主要接口:
-
extern void register_syscore_ops(struct syscore_ops *ops);
//注册syscore回调函数
-
extern void unregister_syscore_ops(struct syscore_ops *ops);
//取消注册的回调函数
-
#ifdef CONFIG_PM_SLEEP
-
extern int syscore_suspend(void);
//回调注册的syscore对象的suspend回调函数
-
extern void syscore_resume(void);
//回调注册的syscore对象的resume回调函数
-
#endif
-
extern void syscore_shutdown(void);
//回调注册的syscore对象的shutdown回调函数
3、具体实现,syscore.c
1)全局变量
-
static LIST_HEAD(syscore_ops_list);
//初始化控制链表头结点,统一管理注册的syscore对象
-
static DEFINE_MUTEX(syscore_ops_lock);
//访问上述链表时,通过此互斥信号量来互斥访问
2)register_syscore_ops:其他组件主要通过此接口来注册回调函数,我们可以看到,把注册的对象存放在了syscore_ops_list链表中。
-
/**
-
* register_syscore_ops - Register a set of system core operations.
-
* @ops: System core operations to register.
-
*/
-
void register_syscore_ops(struct syscore_ops *ops)
-
{
-
mutex_lock(&syscore_ops_lock);
-
list_add_tail(&ops->node, &syscore_ops_list);
-
mutex_unlock(&syscore_ops_lock);
-
}
3)unregister_syscore_ops:与register_syscore_ops功能相反,取消注册,从控制链表中删除。
-
/**
-
* unregister_syscore_ops - Unregister a set of system core operations.
-
* @ops: System core operations to unregister.
-
*/
-
void unregister_syscore_ops(struct syscore_ops *ops)
-
{
-
mutex_lock(&syscore_ops_lock);
-
list_del(&ops->node);
-
mutex_unlock(&syscore_ops_lock);
-
}
4)syscore_suspend:该接口回调所有注册对象的suspend接口,该接口在suspend.c的suspend_enter函数中被调用,执行cpu掉电前的最后阶段操作。
-
/**
-
* syscore_suspend - Execute all the registered system core suspend callbacks.
-
*
-
* This function is executed with one CPU on-line and disabled interrupts.
-
*/
-
int syscore_suspend(void)
-
{
-
struct
syscore_ops *ops;
-
int ret =
0;
-
-
pr_debug(
"Checking wakeup interrupts\n");
-
-
/* Return error code if there are any wakeup interrupts pending. */
-
ret =
check_wakeup_irqs();
-
if (ret)
-
return ret;
-
-
WARN_ONCE(!
irqs_disabled(),
-
"Interrupts enabled before system core suspend.\n");
//我们可以看到,如果此时中断没有屏蔽掉,会有警告产生
-
-
list_for_each_entry_reverse(ops, &syscore_ops_list, node)
//按照链表逆序执行各个注册对象的suspend回调函数
-
if (ops->suspend) {
-
if (initcall_debug)
-
pr_info(
"PM: Calling %pF\n", ops->suspend);
-
ret = ops->
suspend();
-
if (ret)
-
goto err_out;
-
WARN_ONCE(!
irqs_disabled(),
-
"Interrupts enabled after %pF\n", ops->suspend);
-
}
-
-
return
0;
-
-
err_out:
-
pr_err(
"PM: System core suspend callback %pF failed.\n", ops->suspend);
-
-
list_for_each_entry_continue(ops, &syscore_ops_list, node)
//如果有失败的,则执行已经执行过suspend回调的对象的resume回调
-
if (ops->resume)
-
ops->
resume();
-
-
return ret;
-
}
-
EXPORT_SYMBOL_GPL(syscore_suspend);
-
5)syscore_resume:执行注册对象的resume回调,在suspend.c的唤醒流程中被调用
-
/**
-
* syscore_resume - Execute all the registered system core resume callbacks.
-
*
-
* This function is executed with one CPU on-line and disabled interrupts.
-
*/
-
void syscore_resume(void)
-
{
-
struct
syscore_ops *ops;
-
-
WARN_ONCE(!
irqs_disabled(),
-
"Interrupts enabled before system core resume.\n");
-
-
list_for_each_entry(ops, &syscore_ops_list, node)
-
if (ops->resume) {
-
if (initcall_debug)
-
pr_info(
"PM: Calling %pF\n", ops->resume);
-
ops->
resume();
-
WARN_ONCE(!
irqs_disabled(),
-
"Interrupts enabled after %pF\n", ops->resume);
-
}
-
}
6)syscore_shutdown:该接口正常睡眠流程中不涉及调用,主要在sys.c中调用,涉及系统重启、halt等流程。
-
/**
-
* syscore_shutdown - Execute all the registered system core shutdown callbacks.
-
*/
-
void syscore_shutdown(void)
-
{
-
struct
syscore_ops *ops;
-
-
mutex_lock(&syscore_ops_lock);
-
-
list_for_each_entry_reverse(ops, &syscore_ops_list, node)
-
if (ops->shutdown) {
-
if (initcall_debug)
-
pr_info(
"PM: Calling %pF\n", ops->shutdown);
-
ops->
shutdown();
-
}
-
-
mutex_unlock(&syscore_ops_lock);
-
}
边栏推荐
猜你喜欢

deeplab实现自己遥感地质分割数据集
502 bad gateway causes and solutions

3.网页信息解析方法:Xpath与BeautifulSoup

下课看着文档走回实验室,我重新拾起了遗忘的SQL运算符

台达PLC出现通信错误或通信超时或下载时提示机种不符的解决办法总结

ESP8266-Arduino编程实例-MCP9808数字温度传感器驱动

AWS Amazon cloud account registration, free application for 12 months Amazon cloud server detailed tutorial

Read through the interface to call the artifact RestTemplate

拥抱趋势!阿里这套微服务开源框架权威手册,实战到底层细致清晰
给你一个大厂面试的机会,你能面试上吗?进来看看!
随机推荐
「R」使用ggpolar绘制生存关联网络图
准确率(Accuracy)、精度(Precision)、召回率(Recall)和 mAP 的图解
Docker搭建Mysql主从复制
才22岁!这位'00后'博士拟任职985高校!
订song餐系统
一、excel转pdf格式jacob.jar
LeetCode 1161.最大层内元素和:层序遍历
蓝牙协议栈开发板 STM32F1 跑蓝牙协议栈 –传统蓝牙搜索演示以及实现原理[通俗易懂]
关于==和equals的区别和联系,面试这么回答就可以
初始JDBC 编程
一文吃透接口调用神器RestTemplate
keras自带数据集(横线生成器)
2022/7/30
瑞吉外卖项目:新增菜品与菜品分页查询
JVS轻应用的组成与配置
xmind使用指南(XMind具有下列哪些功能)
Read through the interface to call the artifact RestTemplate
AWS亚马逊云账号注册,免费申请12个月亚马逊云服务器详细教程
若枚举映射的值不存在,则不进行反序列化
502 bad gateway causes and solutions
