<meter id="pryje"><nav id="pryje"><delect id="pryje"></delect></nav></meter>
          <label id="pryje"></label>

          新聞中心

          EEPW首頁 > 嵌入式系統(tǒng) > 設(shè)計應(yīng)用 > linux啟動流程導(dǎo)讀(arm為例)

          linux啟動流程導(dǎo)讀(arm為例)

          作者: 時間:2016-11-20 來源:網(wǎng)絡(luò) 收藏
          arm為例,分析一下kernel的啟動過程;

          內(nèi)核版本:linux-3.2.tar.gz

          本文引用地址:http://www.ex-cimer.com/article/201611/318983.htm

          一、arch/arm/kernel/head.s


          .arm

          __HEAD @#define __HEAD .section ".head.text","ax"
          ENTRY(stext)

          THUMB( adr r9, BSYM(1f) ) @ Kernel is always entered in ARM.
          THUMB( bx r9 ) @ If this is a Thumb-2 kernel,
          THUMB( .thumb ) @ switch to Thumb now.
          THUMB(1: )

          setmode PSR_F_BIT | PSR_I_BIT | SVC_MODE, r9 @ ensure svc mode 關(guān)閉普通中斷,快速中斷,使能svc模式
          @ and irqs disabled
          mrc p15, 0, r9, c0, c0 @ get processor id 獲得芯片ID
          bl __lookup_processor_type @ r5=procinfo r9=cpuid 獲得處理器型號,r5 == id,#1
          movs r10, r5 @ invalid processor (r5=0)? 校驗正確性,0錯誤
          THUMB( it eq ) @ force fixup-able long branch encoding
          beq __error_p @ yes, error p

          #ifndef CONFIG_XIP_KERNEL
          adr r3, 2f
          ldmia r3, {r4, r8}
          sub r4, r3, r4 @ (PHYS_OFFSET - PAGE_OFFSET)

          add r8, r8, r4 @ PHYS_OFFSET

          ==========

          #1 :arch/arm/kernel/head-common.h

          ==========


          __CPUINIT
          __lookup_processor_type:
          adr r3, __lookup_processor_type_data @adr 相對偏移讀取,讀取下面type_data地址
          ldmia r3, {r4 - r6} @將該地址存放的值 放入r4(.),r5(begin),r6(end)
          sub r3, r3, r4 @ get offset between virt&phys 鏈接地址-實際地址=偏移量

          ==========

          繼續(xù)arch/arm/kernel/head.s

          ==========


          bl __vet_atags @#1,head-common.s
          #ifdef CONFIG_SMP_ON_UP
          bl __fixup_smp @略
          #endif
          #ifdef CONFIG_ARM_PATCH_PHYS_VIRT
          bl __fixup_pv_table @略
          #endif
          bl __create_page_tables @#2

          ==========

          #1 :arch/arm/kernel/head-common.h

          ==========


          __vet_atags:
          tst r2, #0x3 @ aligned? 不對其就返回
          bne 1f

          ldr r5, [r2, #0] @讀到r5
          #ifdef CONFIG_OF_FLATTREE
          ldr r6, =OF_DT_MAGIC @ is it a DTB? 過濾DTB
          cmp r5, r6
          beq 2f
          #endif
          cmp r5, #ATAG_CORE_SIZE @ is first tag ATAG_CORE? must be first
          cmpne r5, #ATAG_CORE_SIZE_EMPTY
          bne 1f
          ldr r5, [r2, #4]
          ldr r6, =ATAG_CORE
          cmp r5, r6
          bne 1f

          2: mov pc, lr @ atag/dtb pointer is ok

          1: mov r2, #0
          mov pc, lr
          ENDPROC(__vet_atags)

          ============

          @#2:__create_page_tables

          ============


          __create_page_tables:
          pgtbl r4, r8 @ page table address

          ============



          ldr r13, =__mmap_switched @ address to jump to after
          @ mmu has been enabled
          adr lr, BSYM(1f) @ return (PIC) address
          mov r8, r4 @ set TTBR1 to swapper_pg_dir
          ARM( add pc, r10, #PROCINFO_INITFUNC )
          THUMB( add r12, r10, #PROCINFO_INITFUNC )
          THUMB( mov pc, r12 )
          1: b __enable_mmu

          ============

          進入enable_mmu


          __enable_mmu:
          #if defined(CONFIG_ALIGNMENT_TRAP) && __LINUX_ARM_ARCH__ < 6
          orr r0, r0, #CR_A
          #else
          bic r0, r0, #CR_A
          #endif
          #ifdef CONFIG_CPU_DCACHE_DISABLE
          bic r0, r0, #CR_C
          #endif
          #ifdef CONFIG_CPU_BPREDICT_DISABLE
          bic r0, r0, #CR_Z
          #endif
          #ifdef CONFIG_CPU_ICACHE_DISABLE
          bic r0, r0, #CR_I
          #endif
          mov r5, #(domain_val(DOMAIN_USER, DOMAIN_MANAGER) |
          domain_val(DOMAIN_KERNEL, DOMAIN_MANAGER) |
          domain_val(DOMAIN_TABLE, DOMAIN_MANAGER) |
          domain_val(DOMAIN_IO, DOMAIN_CLIENT))
          mcr p15, 0, r5, c3, c0, 0 @ load domain access register
          mcr p15, 0, r4, c2, c0, 0 @ load page table pointer
          b __turn_mmu_on
          ENDPROC(__enable_mmu)

          ==========


          .align 5
          __turn_mmu_on:
          mov r0, r0
          mcr p15, 0, r0, c1, c0, 0 @ write control reg
          mrc p15, 0, r3, c0, c0, 0 @ read id reg
          mov r3, r3
          mov r3, r13 //跳回r13,=__mmap_switched
          mov pc, r3
          __enable_mmu_end:
          ENDPROC(__turn_mmu_on)

          ==========

          #arch/arm/kernel/head-common.s


          __INIT
          __mmap_switched:
          adr r3, __mmap_switched_data

          ldmia r3!, {r4, r5, r6, r7}
          cmp r4, r5 @ Copy data segment if needed
          1: cmpne r5, r6
          ldrne fp, [r4], #4
          strne fp, [r5], #4
          bne 1b

          mov fp, #0 @ Clear BSS (and zero fp)
          1: cmp r6, r7
          strcc fp, [r6],#4
          bcc 1b

          ARM( ldmia r3, {r4, r5, r6, r7, sp})
          THUMB( ldmia r3, {r4, r5, r6, r7} )
          THUMB( ldr sp, [r3, #16] )
          str r9, [r4] @ Save processor ID
          str r1, [r5] @ Save machine type
          str r2, [r6] @ Save atags pointer
          bic r4, r0, #CR_A @ Clear A bit
          stmia r7, {r0, r4} @ Save control register values
          b start_kernel
          ENDPROC(__mmap_switched)

          ===========

          絕對地址操作,copy data,bss清空,跳入start_kernel,進入c環(huán)境。



          關(guān)鍵詞: linux啟動流程ar

          評論


          技術(shù)專區(qū)

          關(guān)閉
          看屁屁www成人影院,亚洲人妻成人图片,亚洲精品成人午夜在线,日韩在线 欧美成人 (function(){ var bp = document.createElement('script'); var curProtocol = window.location.protocol.split(':')[0]; if (curProtocol === 'https') { bp.src = 'https://zz.bdstatic.com/linksubmit/push.js'; } else { bp.src = 'http://push.zhanzhang.baidu.com/push.js'; } var s = document.getElementsByTagName("script")[0]; s.parentNode.insertBefore(bp, s); })();