通常,printk不会在console_init之前打印任何消息,该消息存在于start_kernel中。但是启用early_printk后,printk会在控制台初始化之前开始打印消息。现在,printk的这种行为是如何改变的,因为我仍然使用printk函数来打印调试消息,而不是early_printk函数。这个映射是如何完成的?
发布于 2017-01-13 17:12:38
这并不是真正的地图。当启用early_printk时,使用的printk()和以前一样,在这种情况下只注册新的引导控制台,printk()在早期引导阶段使用它。
看看printk.c。你可以看到:
register_console()函数注册新控制台CON_BOOT标志,因此一旦注册了真正的控制台,就会自动取消注册early_write()函数进行,而printch()函数则分别为每个平台实现。在内核控制台初始化之后,在内核源代码中什么地方禁用了
early_console?
它是在控制台()函数中完成的:
if (bcon &&
((newcon->flags & (CON_CONSDEV | CON_BOOT)) == CON_CONSDEV) &&
!keep_bootcon) {
/* We need to iterate through all boot consoles, to make
* sure we print everything out, before we unregister them.
*/
for_each_console(bcon)
if (bcon->flags & CON_BOOT)
unregister_console(bcon);
}以上代码中的unregister_console()函数禁用了所有引导控制台(注册真正的控制台时)。
真正的控制台在哪里注册?
真正的控制台使用同样的方法注册-- register_console()函数。例如:
CONFIG_SERIAL_8250作为真正的控制台register_console()的位置;它是用init()函数完成的有什么方法可以让引导控制台在控制台初始化后继续运行,禁用真正的控制台?
只有在注册了真正的控制台时,引导控制台才会自动取消注册。按照这个逻辑,您只需要禁用真正的控制台就可以保持引导控制台的完整。
所以,您需要做的是,找出在您的实际控制台中到底使用了哪个驱动程序。您可以查看您的.config文件,也可以查看您的董事会的*_defconfig文件。找到它后,只需在配置中禁用该驱动程序并重新构建内核即可。
如果在这样做之后,您一直在观察某些实际控制台的注册情况,则需要向register_console()添加一些调试打印,以确定正在注册的驱动程序,然后在配置中禁用它。
https://stackoverflow.com/questions/41632166
复制相似问题