STM 32 eCos 시작 코드 분석 (2) 상하 문 전환

최근 에 줄곧 일 하 느 라 바 빴 는데, 지금 은 좀 비 워 서 이 의 제 를 계속 쓰 고 있다.(본문 오리지널 전재 출처 밝 혀 주세요.http://blog.csdn.net/rickleaf)
stm 32 cortexm 3 시스템 구조 에 속 하 는 이상 스 레 드 컨 텍스트 전환 은 반드시 cortexm 3 방식 을 사용 해 야 합 니 다.
열다
packages\hal\cortexm\arch\current\src\context.S
//==========================================================================
// Context switch
//
// R0 contains a pointer to the SP of the thread to load, R1 contains
// a pointer to the SP of the current thread.        
        
        .globl  hal_thread_switch_context
        .thumb
        .thumb_func
        .type   hal_thread_switch_context, %function
hal_thread_switch_context:

        push    {r0-r12,lr}             // Push all savable register
        mov     r2,#2                   // Set state type == thread
        mrs     r3,basepri              // Get priority base register
        mov     r4,sp                   // Get SP (for info only)
        push    {r2-r4}                 // Push them
        
        str     sp,[r1]                 // Save SP

        // Fall through
        
//--------------------------------------------------------------------------
// Load context
//
// This is used to load a thread context, abandoning the current one. This
// function is also the second half of hal_thread_switch_context.

        .globl  hal_thread_load_context
        .thumb
        .thumb_func
        .type   hal_thread_load_context, %function
hal_thread_load_context:

        ldr     sp,[r0]                 // Load SP
        pop     {r2-r4}                 // Pop type, basepri and SP (discarded)
        msr     basepri,r3              // Set BASEPRI
        pop     {r0-r12,pc}             // Pop all register and return

//==========================================================================  

ARM 9 의 컨 텍스트 전환 보다 cortexm 시스템 기구 가 더욱 간결 하 다 는 것 을 알 수 있 습 니 다.
eCos 의 cortexm 이식 중:
R2 현재 작업 의 상 태 를 저장 합 니 다. 예 를 들 어 R2 = 2 는 thread 에서 컨 텍스트 로 전환 하 는 것 을 표시 합 니 다.
R3 스 레 드 우선 순위 표시
R4 는 창고 의 상 태 를 나타 낸다
그리고 ARM 9 의 컨 텍스트 전환 함 수 를 다시 찾 아 보 겠 습 니 다.
packages\hal\arm\arch\current\src\context.S
// ----------------------------------------------------------------------------
//  hal_thread_switch_context
//  Switch thread contexts
//  R0 = address of sp of next thread to execute
//  R1 = address of sp save location of current thread

// Need to save/restore R4..R12, R13 (sp), R14 (lr)

// Note: this is a little wasteful since r0..r3 don't need to be saved.
// They are saved here though so that the information can match the
// HAL_SavedRegisters
        
FUNC_START_ARM(hal_thread_switch_context, r2)
        mov     ip,sp
        sub     sp,sp,#(ARMREG_SIZE - armreg_lr - 4) // skip svc_sp, svc_lr, vector, cpsr, and pc
        stmfd   sp!,{ip,lr}
        stmfd   sp!,{r0-r10,fp,ip}
        mrs     r2,cpsr
        str     r2,[sp,#armreg_cpsr]
        str     sp,[r1]                 // return new stack pointer
#ifdef __thumb__
        b       hal_thread_load_context_ARM // skip mode switch stuff
#endif

        # Now load the destination thread by dropping through
        # to hal_thread_load_context
        
// ----------------------------------------------------------------------------
//  hal_thread_load_context
//  Load thread context
//  R0 = address of sp of next thread to execute
//  Note that this function is also the second half of
//  hal_thread_switch_context and is simply dropped into from it.
        
FUNC_START_ARM(hal_thread_load_context, r2)
        ldr     fp,[r0]                 // get context to restore
        mrs     r0,cpsr                 // disable IRQ's
        orr     r0,r0,#CPSR_IRQ_DISABLE|CPSR_FIQ_DISABLE
        msr     cpsr,r0
        ldr     r0,[fp,#armreg_cpsr]
        msr     spsr,r0
        ldmfd   fp,{r0-r10,fp,ip,sp,lr}
#ifdef __thumb__
        mrs     r1,spsr                 // r1 is scratch 
                                        // [r0 holds initial thread arg]
        msr     cpsr,r1                 // hopefully no mode switch here!
        bx      lr
#else
        movs    pc,lr                   // also restores saved PSR
#endif

 
ARM 9 에서 연속 레지스터 를 저장 하려 면 cortexm 처럼 push 와 pop 이 있어 서 는 안 되 며, 아래 의 두 명령 을 사용 하여 완전히 유사 한 기능 을 사용 해 야 합 니 다.
stmfd
ldmfd 
밑바닥 의 상하 문 보존 방법 을 간단하게 이해 하면 우 리 는 두 개의 서로 다른 체계 구조 가 어떻게 운영 체제 와 인 터 페 이 스 를 연결 하 는 지 이해 할 수 있다.
필 자 는 뒤의 글 에서 eCos 의 ticker 를 소개 함으로써 cortexm 시스템 구조 가 eCos 를 어떻게 사용 하 는 지 계속 깊이 이해 할 것 이다.

좋은 웹페이지 즐겨찾기