안녕하세요. ^^
10차 arm 멤버입니다. head.S에서 압축해제코드 들어가는데 이해가 힘든부분이 있습니다.
좀 엉뚱한 질문일지도 모르겠네요.
uImage의 로드 주소는 아래와 같습니다.
mkimage -l arch/arm/boot/uImage
Image Name: Linux-3.10.0-00621-gb25edd1
Created: Wed Jul 24 16:27:39 2013
Image Type: ARM Linux Kernel Image (uncompressed)
Data Size: 1429440 Bytes = 1395.94 kB = 1.36 MB
Load Address: 0x40008000
Entry Point: 0x40008000
그리고 커널이 풀릴 위치는 아래와 같습니다.
cat arch/arm/mach-exynos/Makefile.boot
zreladdr-y += 0x40008000
params_phys-y := 0x40000100
uboot에서 zImage를 0x40008000에 올리면, head.S가 시작이 되고 zreladdr 위치(0x40008000)에
압축을 풀게 되는데, 그러면 head.S의 코드를 덮어써버리게 되는 것 아닌가요?
왜 zImage 로딩주소와 커널이 풀리는 주소가 같은 걸까요?
압축을 풀기전 덮어쓰게 될경우를 체크해서 재배치(?)하는 코드가 있던데 이게 일반적인 것 같지않아서요.
댓글 2
.
저희 팀에서 분석한 바로는... (제 이해도가 조금 떨어지긴 하지만...^^;;)
처음부터 안겹쳐서 wont_overwrite 로 분기하는 경우가 더 적어보였습니다.
위에서 말씀하신 것처럼 지정한 주소가 비슷하기 때문이죠.
1. 압축풀 이미지의 크기가 앞으로 실행될 코드가 있는 주소를 침범하지 않는 경우에는 그냥 head.S의 현재코드 앞쪽에 커널을 풉니다.
2. 압축 풀 이미지가 실행중인 코드의 끝 주소 이후에 존재하는 경우에도 커널을 그 자리에 풉니다.
3. 하지만 이 두 경우가 아닌 경우에는 압축 풀 주소의 크기만큼을 기존 주소에 더해줍니다.
그리고나서 restart: 로 돌아가서 변경된 r0를 기준으로 모든 값을 다시 계산해주죠.
저희 팀에서 분석하며 설명하는 걸 듣고 처음 감탄했던 부분입니다.
이런 식으로 겹치는 부분을 체크하고 피하는 방법으로 코드를 짠다는 사실에요.^^
그런데 제가 방금 언급한 부분이 정말 도움이 될런지는... 모르겠습니다...^^;;;;
(제가 동문서답한 거라면... 죄송합니다...-.-;;;)