SWI, HandlerLabel 매크로 동작


#분석


1.SWI 명령어를 만나면 0x08번지로 이동.

1
HandleSWI:            .long   (_ISR_STARTADDRESS + 0x8)    // interrupt 함수주소를 획득하여 분기한다.
cs

1
2
3
4
5
6
7
8
9
    _start:
 
    /* ResetHandler가 처음부터 나오는 것이 아니라 
     * vector 주소 영역에는 reset vector가 존재해야 한다
     * exception이 발생하면 ARM은 하드웨어적으로 다음 주소로 분기된다
     */
    b    ResetHandler
    b    HandlerUndef            /* handler for Undefined mode */
    b    HandlerSWI            /* handler for SWI interrupt */
cs


=>    b    HandlerSWI로 이동, 이때 HANDLER 매크로가 등록이 되어있고 매크로를 수행.


1
HANDLER HandlerSWI, HandleSWI
cs


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
    .macro HANDLER, HandlerLabel, HandleLabel
\HandlerLabel:
    sub        sp,sp,#4        /* decrement sp(to store jump address) */
    stmfd    sp!,{r0}            /* PUSH the work register to stack(lr doesn`t push because */ 
                               /* it return to original address) */
    ldr        r0,=\HandleLabel    /* load the address of HandleXXX to r0 */
    ldr        r0,[r0]                 /* load the contents(service routine start address) of HandleXXX */
        
 
    str        r0,[sp,#4]          /* store the contents(ISR) of HandleXXX to stack */
 
    ldmfd    sp!,{r0,pc}         /* POP the work register and pc(jump to ISR) */
    .endm
 
    .text
    .globl_start
cs


=>매크로를 수행하게 되면 pc에 저장된 주소로 jump하게 된다.


1
2
3
4
5
6
7
8
9
extern unsigned int  HandleSWI;
 
HandleSWI    = (unsigned)SWI_Handler;
 
void SWI_Handler(void)
{
    Uart_Printf("SWI exception.\n");
    for(;;);
}
cs



■그림으로 보는 동작 과정




+ Recent posts