AAPCS 규약에 따르면, 호출된 함수(Callee)가 호출한 함수로 돌아가기 전에 원래값으로 복구해야 하는 reg set이 있다.
r4-r8, r10, r11 and SP(r13) (and r9 in PCS variants that designate r9 as v6)
이 reg들은 호출된 함수가 원래 상태로 돌려놔야 한다.
PendSV같은 context switching routine이 이 부분을 저장/복구하는 이유.반대로, r0-r3, r12, LR(r14), PC(r15), xPSR : 총 8개는 호출한 함수(Caller)가 보존해야하는 레지스터들이다. 이를 HW conetxt frame이라고 부른다.
또한, [C]PSR은 전역 reg라서, flag[4:0](N, Z, C, V, Q) in [31:27] bits와 GE[3:0] bits in [19:16] bits는 함수 진입이나 복귀 시 정의되지 않는다. (이 비트들은 최근 비교 등에 대한 상태를 전달함) 이는 곧, 해당 reg에 필요한 상태를 보존하는 책임 역시 Caller에게 있음을 의미한다.
Stack은 double-word aligned이어야 한다. 이는 곧 함수에 진입할 때 스택이 항상 8바이트 정렬로 시작해야 한다는 뜻이다.
Summary
Interrupt에서의 실행이 Abstract Binary Interface에 부합하려면, ARM Architecture는 stack을 항상 8바이트로 정렬하고, caller가 r0-r3, r12, r14 상태를 저장해야 한다. 이를 수행하기 위해 ARM Cortex-M Core는 이 Context를 스택에 자동으로 push한다.
r0~e3 : 함수 인자 전달용
r12 : 임시용
LR : 리턴 주소
PC : 복귀할 명령어
xPSR : 프로그램 상태 레지스터, 실행 상태 플래그 포함
exception에서 exit할 때, 하드웨어에게 어떤 state를 복구할 지 설명해줘야 한다.
이 때 EXC_RETURN이 link register(lr)로 로드되어야 한다.
보통은 exception 진입시에 lr에 있던 값을 그대로 보여준다. 하지만, Thread mode sp를 바꾸기 위해서 다르게 저장할 수도 있다.
EXC_RETURN V | Mode to Return to | Stack to use
ㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡ
0xFFFFFFF1 | Handler mode | MSP
0xFFFFFFF9 | Thread mode | MSP
0xFFFFFFFD | Thread mode | PSP
ㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡ
더 있는데, FP는 아직 서비스에 포함하지 않을 예정이므로 스킵.
스위칭이 발생할 때, 현재 태스크의 state를 저장해야 한다. 이 때 저장 항목으로는 태스크의 실행 상태와 현재 사용 중인 하드웨어 레지스터값들이 포함된다.