亚洲av成人无遮挡网站在线观看,少妇性bbb搡bbb爽爽爽,亚洲av日韩精品久久久久久,兔费看少妇性l交大片免费,无码少妇一区二区三区

  免費(fèi)注冊(cè) 查看新帖 |

Chinaunix

  平臺(tái) 論壇 博客 文庫(kù)
最近訪問(wèn)板塊 發(fā)新帖
查看: 1507 | 回復(fù): 0
打印 上一主題 下一主題

Linux關(guān)機(jī)重啟流程分析 [復(fù)制鏈接]

論壇徽章:
0
跳轉(zhuǎn)到指定樓層
1 [收藏(0)] [報(bào)告]
發(fā)表于 2010-02-23 16:41 |只看該作者 |倒序?yàn)g覽
linux下的關(guān)機(jī)和重啟流程對(duì)于一般的桌面應(yīng)用和網(wǎng)絡(luò)服務(wù)器來(lái)說(shuō)并不重要,但是在用戶(hù)自己定義的嵌入式系統(tǒng)內(nèi)核中就有一定的研究意義,通過(guò)了解Linux 關(guān)機(jī)重啟的流程,我們對(duì)它可以修改和自定義,甚至以此為基礎(chǔ)開(kāi)發(fā)出全新的功能來(lái)。
    1.概述
    在linux下的關(guān)機(jī)和重啟可能由兩種行為引發(fā),一是通過(guò)用戶(hù)編程,一是系統(tǒng)自己產(chǎn)生的消息。用戶(hù)和系統(tǒng)進(jìn)行交互的方式也有兩個(gè),一個(gè)是系統(tǒng)調(diào)用:sys_reboot,另一個(gè)就是apm或則acpi的設(shè)備文件,通過(guò)對(duì)其操作也可以使系統(tǒng)關(guān)機(jī)或者重啟。
    2.通過(guò)系統(tǒng)調(diào)用sys_reboot的重啟
    這個(gè)系統(tǒng)調(diào)用定義了一系列的MAGIC_NUMBER,在調(diào)用的開(kāi)始部分首先檢查MAGIC_NUMBER是否正確,只有正確才繼續(xù)向下運(yùn)行。在重啟的時(shí)候轉(zhuǎn)向分支
    case LINUX_REBOOT_CMD_RESTART:
    首先使用notifier_call_chain向其它部分發(fā)出重啟的消息,然后調(diào)用machine_restart函數(shù)完成重啟。
    machine_restart函數(shù)的開(kāi)始部分有一段SMP相關(guān)的代碼,主要完成多CPU時(shí)由一個(gè)CPU完成重啟操作,其它CPU處于等待狀態(tài)。之后系統(tǒng)根據(jù)一個(gè)變量reboot_thru_bios的內(nèi)容判斷重啟方式,通過(guò)閱讀reboot_setup我們可以得知,這個(gè)參數(shù)的內(nèi)容是在系統(tǒng)啟動(dòng)時(shí)指定的,決定了是否利用bios,事實(shí)上是系統(tǒng)復(fù)位后的入口(FFFF:0000)地址的程序進(jìn)行重啟。在不通過(guò)bios進(jìn)行重啟的情況下,系統(tǒng)首先設(shè)定了重啟標(biāo)志,然后向端口0xfe寫(xiě)入數(shù)字0x64,這種重啟的具體原理我還不大清楚,似乎是模擬了一次reset鍵的按下,希望大家和我討論。在通過(guò)bios重啟的情況下,系統(tǒng)同樣先設(shè)定了重啟模式,然后切換到了實(shí)模式,通過(guò)一條ljmp $0xffff,$0x0完成了重啟。
    3.通過(guò)系統(tǒng)調(diào)用sys_reboot進(jìn)行關(guān)機(jī)
    在系統(tǒng)調(diào)用的處理分支上,我們可以看到,首先同樣是檢查MAGIC_NUMBER,然后在
    case LINUX_REBOOT_CMD_POWER_OFF:
    的執(zhí)行流程里面,又是使用notifier_call_chain發(fā)出了關(guān)閉計(jì)算機(jī)電源的消息,緊接著執(zhí)行了machine_power_off函數(shù)。我們?cè)趍achine_power_off函數(shù)中可以看到,如果pm_power_off這個(gè)函數(shù)指針不為空,那么系統(tǒng)就會(huì)通過(guò)調(diào)用這個(gè)函數(shù)進(jìn)行關(guān)機(jī)。在apm已經(jīng)加載的情況下(SMP除外),實(shí)際上pm_power_off函數(shù)實(shí)際上指向了apm.c中的apm_power_off,在這個(gè)函數(shù)里系統(tǒng)通過(guò)apm_info結(jié)構(gòu)里的值,使用切換到實(shí)模式關(guān)機(jī),或者使用apm_bios_call_simple函數(shù)調(diào)用保護(hù)模式下的apm接口關(guān)機(jī)兩種方法。
    4.apm驅(qū)動(dòng)本身的關(guān)機(jī)過(guò)程
    apm使用其注冊(cè)的設(shè)備的ioctl接口完成apm的操作,在apm.c的do_ioctl函數(shù)中可以看見(jiàn)處理的分支。這里只有suspend和standby的代碼,所以我們不能通過(guò)ioctl這種方法使用apm關(guān)機(jī)。
    當(dāng)用戶(hù)按下POWER開(kāi)關(guān)的時(shí)候,如果有apm模塊,那么關(guān)機(jī)流程是由apm來(lái)處理的。apm驅(qū)動(dòng)在初始化的時(shí)候啟動(dòng)了一個(gè)apm內(nèi)核線程:apm_mainloop,系統(tǒng)會(huì)在這里檢測(cè)到POWEROFF按鍵消息并且將其命名為APM_SYS_SUSPEND,以區(qū)別apm -s設(shè)置的APM_USER_SUSPEND模式。緊接著進(jìn)入了apm_event_handler函數(shù),又從apm_event_handler函數(shù)進(jìn)入了check_events函數(shù),處理函數(shù)對(duì)應(yīng)的case分支上。系統(tǒng)同樣使用了suspend函數(shù)進(jìn)行關(guān)機(jī),不過(guò)由于其它參數(shù)的原因,suspend最后調(diào)用的是關(guān)機(jī)的流程。
    5.解決問(wèn)題實(shí)例
    1)按POWER鍵時(shí)某些主板死機(jī)
    經(jīng)查只有某些特定的驅(qū)動(dòng)裝載之后才會(huì)出現(xiàn)這樣的情況,并且當(dāng)使用關(guān)機(jī)系統(tǒng)調(diào)用sys_reboot的時(shí)候沒(méi)有這樣的問(wèn)題。分析apm的處理流程,懷疑是在關(guān)機(jī)前驅(qū)動(dòng)程序沒(méi)有正確處理apm發(fā)出的詢(xún)問(wèn)消息造成的。由于部分驅(qū)動(dòng)程序沒(méi)有源代碼,決定hack掉apm.c的關(guān)機(jī)部分,讓兩種方式的關(guān)機(jī)走同樣的流程。于是把a(bǔ)pm.c的check_events函數(shù)中對(duì)APM_SYS_SUSPEND部分改寫(xiě)為如下代碼:
    ret = exec_usermodehelper(poweroff_helper_path, argv, envp);
    if (ret) {
    printk(KERN_ERR
    "apm.c: failed to exec %s , errno = %d\\n",
    poweroff_helper_path, errno);
    }
    break;
    For fast reboot support
    static unsigned char fast_reboot_switch [] =
    {
    0x66, 0x0f, 0x20, 0xc0, /* movl %cr0,%eax */
    0x66, 0x25, 0x10, 0x11, 0x11, 0x11, /* andl $0x11111110,%eax */
    0x66, 0x0f, 0x22, 0xc0, /* movl %eax,%cr0 */
    0xea, 0x00, 0x00, 0x00, 0x70 /* ljmp $0x7000,$0x0000 */
    };
    系統(tǒng)就可以切換到實(shí)模式中,然后跳轉(zhuǎn)到7000H:0位置開(kāi)始執(zhí)行。
    6.ACPI概述
    在2.4.20內(nèi)核中ACPI模塊被注明為試驗(yàn)和未完成,里面有一部分功能也許沒(méi)有實(shí)現(xiàn)。如果APM和APCI兩個(gè)模塊同時(shí)編譯進(jìn)內(nèi)核,APM在ACPI前被加載,APM起作用使ACPI退出。對(duì)于系統(tǒng)電量、電源實(shí)踐一類(lèi)的支持(主要是在筆記本上有用),靠的是acpid這個(gè)daemon程序。
    沒(méi)有一個(gè)功能類(lèi)似apm的應(yīng)用程序切換狀態(tài),acpi的程序僅僅完成了對(duì)acpi狀態(tài)的查詢(xún)。用戶(hù)實(shí)現(xiàn)S0-S4的功能可以直接向/proc/acpi/sleep文件中寫(xiě)入數(shù)字來(lái)實(shí)現(xiàn)。通過(guò)讀出(cat)其中的內(nèi)容可以知道系統(tǒng)到底支持那些模式。
    acpi模塊的源代碼主程序在linux/drivers/acpi/driver.c中,如果向sleep文件寫(xiě)東西,就轉(zhuǎn)到了linux/drivers/acpi/ospm/system/sm_osl.c文件的sm_osl_proc_write_sleep函數(shù)中,這個(gè)函數(shù)后來(lái)調(diào)用了sm_osl_suspend函數(shù)。在這個(gè)函數(shù)里完成了各種功能,包括保護(hù)各種狀態(tài)。最后真正的sleep是通過(guò)對(duì)acpi_enter_sleep_state的調(diào)用完成的,這個(gè)函數(shù)在linux/drivers/acpi/hardware/hwsleep.c文件中,這里寫(xiě)了acpi的寄存器使系統(tǒng)進(jìn)入sleep狀態(tài)。寫(xiě)寄存器的指令在這個(gè)目錄下面的hwregs.c中。
    7.總結(jié)
    本文對(duì)acpi的介紹非常簡(jiǎn)略,實(shí)際上ACPI必定會(huì)成為將來(lái)linux內(nèi)核中首選的電源管理方式。由于目前官方代碼中ACPI版本較低,所以沒(méi)有太詳細(xì)的論述,希望將來(lái)的內(nèi)核能有所改變。


本文來(lái)自ChinaUnix博客,如果查看原文請(qǐng)點(diǎn):http://blog.chinaunix.net/u3/111988/showart_2185256.html
您需要登錄后才可以回帖 登錄 | 注冊(cè)

本版積分規(guī)則 發(fā)表回復(fù)

  

北京盛拓優(yōu)訊信息技術(shù)有限公司. 版權(quán)所有 京ICP備16024965號(hào)-6 北京市公安局海淀分局網(wǎng)監(jiān)中心備案編號(hào):11010802020122 niuxiaotong@pcpop.com 17352615567
未成年舉報(bào)專(zhuān)區(qū)
中國(guó)互聯(lián)網(wǎng)協(xié)會(huì)會(huì)員  聯(lián)系我們:huangweiwei@itpub.net
感謝所有關(guān)心和支持過(guò)ChinaUnix的朋友們 轉(zhuǎn)載本站內(nèi)容請(qǐng)注明原作者名及出處

清除 Cookies - ChinaUnix - Archiver - WAP - TOP