kernel.h
/* Values used for system_state */
extern enum system_states {
SYSTEM_BOOTING,
SYSTEM_RUNNING,
SYSTEM_HALT,
SYSTEM_POWER_OFF,
SYSTEM_RESTART,
SYSTEM_SUSPEND_DISK,
} system_state;
main.c
enum system_states system_state __read_mostly;
EXPORT_SYMBOL(system_state);
static noinline int init_post(void)
{
。。。。。。。。
system_state = SYSTEM_RUNNING;
。。。。。。。。
。。。。。。。。。。。。。。。。。。。。。
注:第一个用户空间进程init启动之前,系统都处于SYSTEM_BOOTING状态, 之后转入SYSTEM_RUNNING状态 !
。。。。。。。。。。。。。。。。。。。。
run_init_process("/bin/init");
。。。。。。。。。。。。。。。。。。
panic("No init found. Try passing init= option to kernel. "
"See Linux Documentation/init.txt for guidance.");
}
锁,任务调度,sleep 等逻辑在kernel启动阶段是不希望不出的。
但有时为让一段代码在kernel启动阶段和运行阶段都可以正常工作,此时system_state就很好用了。
int blocking_notifier_chain_register(struct blocking_notifier_head *nh,
struct notifier_block *n)
{
int ret;
/*
* This code gets used during boot-up, when task switching is
* not yet working and interrupts must remain disabled. At
* such times we must not call down_write().
*/
if (unlikely(system_state == SYSTEM_BOOTING))
return notifier_chain_register(&nh->head, n);
down_write(&nh->rwsem);
ret = notifier_chain_register(&nh->head, n);
up_write(&nh->rwsem);
return ret;
}