시스템 소프트웨어 개발을 위한 Arm 아키텍처의 구조와 원리 (155) 썸네일형 리스트형 [리눅스커널] 라즈비안: vmlinux 소스 코드 정보 추가 : CONFIG_DEBUG_INFO 리눅스 커널 코드를 빌드하면 vmlinux란 파일이 추출됩니다. 바이너리 유틸리티를 활용하면 vmlinux에서 여러 디버깅 정보 확인을 할 수 있는데요. 아래 컨피그를 추가하면 vmlinux 심볼 테이블에 소스 코드 정보가 추가됩니다. diff --git a/arch/arm/configs/bcm2709_defconfig b/arch/arm/configs/bcm2709_defconfig index 96fbcc6..961829b 100644 --- a/arch/arm/configs/bcm2709_defconfig +++ b/arch/arm/configs/bcm2709_defconfig @@ -31,6 +31,7 @@ CONFIG_KPROBES=y CONFIG_JUMP_LABEL=y CONFIG_MODULES.. arm32 - Unwind Idx/prolog 소개 TRACE32는 어떻게 각 함수마다 어떤 register를 stack에 push를 하고 지역 변수를 위해서 얼마 만큼의 공간을 확보하는지를 알까요? 모든 함수의 prolog를 체크하여 위 과정을 수행할까요? 그러기에는 과정들이 매우 복잡하므로, Build 과정에서 위의 prolog 정보를 미리 저장해둬요. Linux Kernel의 Symbol Table중에서 __start_unwind_idx에서부터 __stop_unwind_idx 영역이 있는데요. TRACE32명령창에 symbol.browse *unwind_idx 을 입력하면 해당 Symbol Table을 확인할 수 있어요. symbol___________________|type_____________________|address_____________.. ARM64- Stack Push Userspace -> Kernel Space 코드리뷰 유저 공간에서 실행된 레지스터가 커널 Bottom Stack에 Push 되는 디버깅 정보를 예전 페이지에 업데이트했잖아요. 아래와 같은 메모리 덤프를 확인했었죠.(출처:http://rousalome.egloos.com/9966225) NUD:FFFFFFE4DE6A7EB8| 3C 6B 77 2B 46 76 A8 C2 0xC2A876462B776B3C NUD:FFFFFFE4DE6A7EC0| 45 00 00 00 00 00 00 00 0x45 // x0 NUD:FFFFFFE4DE6A7EC8| 80 37 81 AF 7B 00 00 00 0x7BAF813780 // x1 NUD:FFFFFFE4DE6A7ED0| 16 00 00 00 00 00 00 00 0x16 // x2 NUD:FFFFFFE4DE6A7ED8| 4.. ARM64 - 프로세스(Process) preempt_disable(), preemption 스케줄(Schedule) 조건 분석 아래 제 블로그에서 ARM32 아키텍처에서 preempt_disable() 매크로 함수를 호출하면 __irq_svc 벡터에서 svc_preempt 함수를 호출하지 않아, preemption이 수행되지 않는다고 확인했어요. http://rousalome.egloos.com/9964816 이번에는 ARM64(Aarch64) 아키텍처에서는 어떤 코드로 구현 되는지 살펴 볼께요. ARM64(Aarch64) 아키텍처는 ARM32 아키텍처와는 다르게 아예 어떤 코드가 실행이 되던 current_thread_info을 읽어올 수 있는 Instruction을 제공해요. 코드는 아래와 같은데, "mrs" 명령어로 스택 Top 주소를 가져오네요. current_thread_info()가 호출될 때 속도를 더 빠르게 하기 .. ARM64 - ttrb0 Special Register 설정 건 current_thread_info를 보면 ttbr0 레지스터 확인을 할 수 있거든요. (리눅스 커널 버젼: 4.4 이상) (struct thread_info *) (struct thread_info*)(0xFFFFFFE5783BFEE0 & ~0x3fff) = 0xFFFFFFE5783BC000 = (long unsigned int) flags = 0 = 0x0 = '........', (mm_segment_t) addr_limit = 549755813888 = 0x0000008000000000 = '........', (struct task_struct *) task = 0xFFFFFFE57839B000 = -> ((long int) state = 0 = 0x0 = '........', (u64) ttb.. ARM64(Aarch64) - 함수 호출시 Stack Push(스택 푸쉬) 규약 아래와 같은 콜 스택에서 유저 공간에서 돌던 레지스터 Stack Push와 Exception 발생 시 Stack Push에 대해서 살펴봤어요. 이제는 평상시 함수 호출 시 어떻게 Stack Push를 하는 지 점검하려고 해요. 자 계속 그 동안 다뤄왔던 아래 "rild"란 프로세스의 콜스택에서 rpi_ipc_router_sendmsg()-> rpi_ipc_router_send_to() 으로 함수가 호출된 후 스택 푸쉬가 어떻게 수행되는 지 점검해볼께요. -000|do_mem_abort() -001|el1_da(asm) -->|exception -002|ch_pop_remote_rx_intent() -003|glink_tx_common() -004|glink_txv() -005|ipc_router_glin.. ARM64- 스택 푸쉬(Stack Push) Userspace -> Kernel Space 유저 스페이스에서 커널 스페이스로 전환하려면 시스템 콜을 호출해야 한다 것은 마르고 닳도록 들었죠? 이번에는 ARM64 Architecture에서 EL0 ->EL1로 변환될 시, Stack을 어떻게 Push하는 지 살펴볼께요. "rild"란 프로세스의 콜스택을 예를 들어 볼 께요. 잘 보면, 유저 공간에서 sendto란 시스템 콜을 호출했다는 걸 알 수 있네요. -000|do_mem_abort() -001|el1_da(asm) -->|exception -002|ch_pop_remote_rx_intent() -003|glink_tx_common() -004|glink_txv() -005|ipc_router_glink_xprt_write() -006|msm_ipc_router_write_pkt(inline).. ARM64(Aarch64) - Special Register 설정(Trace32) AArch64 64비트 아키텍쳐에서 설정해야 할 Special Register에 대해서 잠깐 살펴볼께요. 우선 커널이 구동될 때의 Exception Level이 1이니까 EL1 모드만 점검하죠. TTBR1_EL1 약자는 Translation Table Base Register인데, 가상주소와 물리주소를 변환할 때 쓰이죠. Trace32로 이 레지스터를 설정하고 싶으면 아래 커맨드를 써야 하지오. Data.Set SPR:0x30201 %Quad 0x82ba1000 // TTBR1_EL1 TCR_EL1 Translation Control Register의 약자인데 Stage 1 가상 주소 Translation 시 필요한 Translation 베이스 레지스터 정보를 포함하고 있어요. Trace32로 이 레지스.. 이전 1 ··· 16 17 18 19 20 다음