1. 程式人生 > >新路程------imx6q的reboot過程

新路程------imx6q的reboot過程

   之前的看門狗時好時壞,最後發現是輸出wdog_B的電容過小導致低電平時間太短,於是看了一下為什麼reboot命令最後會以拉低這個gpio為結果,參考程式碼分析:

   reboot先來到

/kernel/sys.c中
void kernel_restart(char *cmd)
{
kernel_restart_prepare(cmd);
if (!cmd)
printk(KERN_EMERG "Restarting system.\n");
else
printk(KERN_EMERG "Restarting system with command '%s'.\n", cmd);


kmsg_dump(KMSG_DUMP_RESTART);
machine_restart(cmd);
}

然後到了arch/arm/kernel/process.c裡

void machine_restart(char *cmd)
{
machine_shutdown();
arm_pm_restart(reboot_mode, cmd);
}

然後到了void (*arm_pm_restart)(char str, const char *cmd) = arm_machine_restart,

然後是

arch_reset(mode, cmd);

然後到了System.c (arch\arm\plat-mxc):void arch_reset(char mode, const char *cmd)

然後

void arch_reset(char mode, const char *cmd)
{
unsigned int wcr_enable;


arch_reset_special_mode(mode, cmd);


#ifdef CONFIG_ARCH_MX6
/* wait for reset to assert... */
if (enable_ldo_mode == LDO_MODE_BYPASSED) {
/*On Sabresd board use WDOG2 to reset external PMIC, so here do
* more WDOG2 reset.*/
wcr_enable = 0x14;

__raw_writew(wcr_enable, IO_ADDRESS(MX6Q_WDOG2_BASE_ADDR));
__raw_writew(wcr_enable, IO_ADDRESS(MX6Q_WDOG2_BASE_ADDR));
} else
wcr_enable = (1 << 2);
__raw_writew(wcr_enable, wdog_base);
/* errata TKT039676, SRS bit may be missed when
SRC sample it, need to write the wdog controller
twice to avoid it */
__raw_writew(wcr_enable, wdog_base);


/* wait for reset to assert... */
mdelay(500);


printk(KERN_ERR "Watchdog reset failed to assert reset\n");


return;
#endif到了最後去動了watchdog2的wdog_B輸出,請參考watchdog的暫存器這個功能是

Assert WDOG output.