본문 바로가기

Server/linux공통

커널(kernel)의 이해

주요내용

kernel update

kernel source 구하기

kernel compile

kernel patch

bootloader에 새로운 kernel image infomation 추가하기

 

1.kernel version의 이해

리눅스 커널은 리누스 토발즈(linus tovaldz)에 의해서 최초로 개발된 이래, 수많은 기능과 버그를 보완하면서

커널이 1.x 버전 2.x를 걸쳐 3.8 버전까지 공개 되었습니다.

숫자가 홀수는 개발버전 짝수는 안정버전으로 분류

 

2.리눅스 배포판 커널과 업그레이드 방법

리눅스 배포판 커널

리눅스 배포판에 들어가는 커널은 순수 커널에 배포판 개발 업체에서 일부 기능을 수정하거나 보완한 패치를 적용한

변경된 커널입니다 같은 순수 커널 버전일지라도 배포판 개발자에 의해서 커널이 변경되기 때문에 배포판마다 커널이 조금씩 차이가 있기 마련입니다. 

커널버전은 확인하고자 할 때는 uname 명령을 사용합니다.

 

옵션 설명
-a 모든 정보 보여주기
-r 버전명만 보여주기
-s 커널명만 보여주기
-m 커널 머신명 보여주기
-p CPU type 보여주기
-o OS 정보
--help 도움말

 

배포판 커널 업그레이드

xWindows의 시냅틱 패키지 관리자 실행

root권한이 필요합니다.

kernel- 검색 (미검색시 버전나온게없음을 의미)

테스트 버전을 추가하기 위해[설정]-[저장소] 

저장소 가운데 ftp.jaist.ac.jp 저장소를 찾아 클릭 

[분류]에 testing 추가

다시불러오기

램용량4기가 이상(.pae) 이하(.bfs) 설치

uname -r 명령어로 변경된 버전 확인

 

배포판 커널 설치 위치

/boot 디렉토리에 커널 이미지인 vmlinuz-3.4.25-pclos1.bfs 파일이 설치되며 일종ㅇ에 각종 드라이버라고 할수있는 모듈 들이

/lib/modules/커널버전명 디렉토리에 설치됩니다. 

커널을 포함하고 있는 패키지 안에는 어떤 것들이 있으며, 어느 경로로 설치되는지를 다음 명령으로 확인해 봅니다.

rpm -ql kernel-'uname -r' | more

 

커널이미지 : /boot/vmlinuz-커널버전명

커널 모듈 : /lib/modules/커널버전명

 

플리마우스를 위한 initrd.img 이미지 업데이트

커널 업데이트 후 재부팅시 부트 스플래시인 플리마우스 테마가 바뀌어 이상하게 나오는 경우가 발생한다.

변경된 플리마우스 테마를 기존의 플리마우스 테마로 되돌리기 위해서는 플리마우스를 다시 설정해 주면 됩니다.

앞 장"부트 과정의 이해"에서 플리마우스 테마를 설정하는 방법으로는 다음과 같이 -R옵션을 사용했습니다만

여기서는 -R 옵션의 이해를위해 사용하지않고 플리마우스 테마를 복구하는과정을 알아봅시다.

 

 플리마우스 테마로 7(테마명)을 설치 기본테마로지정

#plymouth-set-default-theme 7

명령갱신

#/usr/share/bootsplash/scripts/make-boot-splash-raw /boot/initd-'uname-r'.img 7

make-boot-splash-raw은 부트스플래시를 적용한 initrtd 이미지를 생성해 주는 명령 형식

make-boot-splash-raw </경로/initrtd파일명> <플리마우스테마명>

 -R 옵션 미사용시 mkinitrd 명령이 아닌 make-boot-splash-raw명령을 이용합니다.

 

커널 소스 다운로드 및 설치

ftp.kernel.org 서버로부터 커널 최신 소스를 다운로드하여 압축을 해제하여 설치하는 과정을 따라합니다.

 

최신커널 소스를 다운받습니다.

weget 이용 다운로드

weget ftp://ftp.kernel.org/pub/linux/kernel/v3.x/커널버전명.tar.xz

 

다운로드한 파일을 /usr/src/linux 디렉토리로 압축을 풉니다 이 때 다운로드한 커널 파일은 tar.xz 파일형식을 압축을풉니다.

# tar xvfx linux-3.8.1.tar.xz -C /usr/src

 

/usr/src 디렉토리로 이동하면 linux-3.8.1 디렉토리가 존재하는데, 이를 linux 경로로 심볼릭 링크를 걸어놈

 

커널 컴파일 환경 준비

커널 컴파일(kernel compile): 커널소스에서 제공하는 설정 요소들 가운데 시스템에 맞는 설정 요소들을 설정하여 컴파일러를 통해

새로운 커널 이미자와 모듈을 생성하는 과정 커널컴파일을위해서 커널 소스가 설치되어 있으야 하며

다음과 같은 컴파일 환경에 필요한 패키지들이 설치되어 있어야 합니다.

 

패키지 권장버전 버전체크방법 RPM 패키지 버전
GNU gcc 4.5 이상 gcc --version gcc-4.5.2-4pclos2011
make 3.81 이상 make --version make-3.81-3pclos2010
binutils 2.20 이상 ld -v binutils-2.21.52.0.2-2pclos2011
module-init-tools 3.0 이상 depmod -V module-init-tools-3.6-6pclos2011
util-linux-ng 2.10o fdformat --version util-linux-ng-2.18-2pclos2010
e2fsprogs 1.29 tune2fs e2fsprogs-1.42-2pclos2011
procps 3.2.0 ps --version procps-3.2.8-1pclos2010

 

 

커널 컴파일 과정

 make menuconfig -> make -> make modules_install -> make install

 

커널 설정 초기화

make mrproper 명령은 커널 소스를 원상태로 초기화시킬 때 사용하는 명령으로, 이미 설정된 커널 설정 값을

모두 초기화시키고, 컴파일된 오브젝트(object,.ko 확장자를 가진 파일, 이를 커널에서 모듈이라고 함) 파일들을 모두

제거하여 커널 상태를 원래의 소스 상태로 되돌려 놓는 초기화 명령입니다. 커널 소스를 다시 설치하지 않고 커널

소스 원 상태로 되돌려 놓지 않는 이상 이 명령은 자주 쓰이는 명령은 아니므로 커널 컴파일 과정 순서에는 미포함되어있다.

 

커널 메뉴 설정

make menuconfig, make xconfig, make gconfig 등 다양한 방법으로 커널 메뉴 설정을 할 수 있습니다.

makeconfig와 gconfig는 각각 QT라이브러리와 GTK+2라이브러리를 이용하여 그래픽 환경으로 커널 메뉴를 설정할 수 있게 해 주지만, 커널 메뉴 설정은 그래픽 환경으로 설정한느 것 보다는 make menuconfig을 이용 하여 텍스트환경으로 설정하는것이 더 간편합니다.

make help 명령을 실행하면 커널 메뉴 설정 명령에 대한 자세한 도움말을 구할 수 있습니다.

 

방법 실행환경 특징
make oldconfig 콘솔, 엑스 텍스트로 각 커널 옵션 일일히 선택
make menuconfig 콘솔, 엑스 텍스트 환경으로 각 커널 메뉴 선택
make xconfig 엑스전용 QT기반 그래픽 커널 메뉴 설정 환경
make gconfig  엑스전용 GTK+2 기반의 그래픽 커널 메뉴 설정 환경
make defconfig 콘솔, 엑스 모든 옵션을 기본값 적용
make allmodconfig 콘솔, 엑스 모든 옵션을 가능한 모듈로 선택하여 설정
make allyesconfig 콘솔, 엑스 모든 옵션을 yes로 설정, 비바람직한 설정
make allnoconfig 콘솔, 엑스 모든 옵션을 최소 상태로 설정 비바람직한 설정

 

 

커널 메뉴 설정 규칙

커널 메뉴 및 요소를 설정하는 규칙으로는 y 또는 * 와 M,N 이 있습니다.

 

엔터키 커널메뉴선택
Y 또는 * 커널에 적재(built-in 되도록 메뉴 또는 요소 선택)
M 모듈로 컴파일되도록 메뉴 또는 요소 선택
N 선택하지 않음, N은 표시되지 않고, 어떠한 체크도 하지않음

 

해당설정을 *로 선택하여 커널에 적재한다는 의미는 커널 이미지에 해당 기능을 포함시켜 컴파일한다는 의미

커널에 해당기능이 적재되면, 모듈 유틸리티(insmod 또는 modprobe)로 해당 기능을 띄우지 않고서도 자동실행됨을 말합니다.

M으로 선택하면 해당 기능에 대해서 모듈로 컴파일 한다는 의미이며, 이것은 모듈 유틸리티로 컴파일된 모듈을 띄어 주지 않으면 동작되지 않음을 의미합니다.

커널 메뉴를 선택하는데 있어서 불필요한 기능들은 커널에 적재되지 않도록 하는 것이 좋습니다.

시스템 부팅시 커널에 의해서 꼭 실행되어야 하는 기능이 아닌 것은 가능한 모듈로 선택하고, 필요할 떄마다 모듈 유틸리티로 띄어서

사용 하는 것이 바람직합니다. 커널 메뉴를 설정하는데 있어서 잘 모르는 옵션이나, 불필요하지 않은 옵션들은 선택하지 않거나 향후에 필요로 할 것이므로 대비하여 모듈로 선택합니다.

make menuconfig 의 설정 인터페이스에서 각 메뉴는 방향키를 사용하여 이동하고, 메뉴의 선택은 enter키를 사용하며 커널 옵션 선택은

space 키를 사용하여 커널 포함(*),모듈 선택(M),선택하지 않음(N) 결정합니다. 커널은 하드웨어와 밀접한 관련이 있고, 네트워크에 대한 지식을 요구하기 때문에 커널 파일을 처음 하는 사용자에게는 커널 컴파일 설정은 매우 복잡하고 이해하기 어려운 부분입니다.

그래서 이 책에는 모든 커널 옵션을 다루기 보다는 커널 옵션을  선택하년 일반적인 방법과 커널 컴파일 방법과 부트로더에 올리는 방법등 기본 지식만 다룹니다.

 

커널 옵션 설정

옵션 카테고리 간단한 설명
Code maturity level option 개발 중의 코드 및 드라이버 사용 선택 유무
General setup 커널에 대한 일반적인 설정
Loadable module support 모듈 적재에 관한 설정
Block layer 블록 장치에 활성 및 해제에 관한 설정
Processor type and features CPU 및 메모리 기능에 관한 설정
Power management option 절전 기능에 관한 설정
Bus options 메인보드의 PCI,EISA, PCMCIA 지원 설정
Executeable file formats 커널 지원 가능한 바이너리 형태 설정
Networking 네트워크 기능 지원에 관한 설정
Device Drivers HDD,SCSI,네트워크 멀티미디어 장치 드라이버 설정
File sytems 커널 지원 파일 시스템 설정
Instrumentation Support 커널 지원 프로필 지원 설정
Kernel hacking 커널 해킹 설정
Security option SELINUX 커널 보안 옵션 설정
Crytographic option 암호화 및 인증에 관련된 알고리즘 모듈 설정
Library routines

외부 모듈의 라이브러리 함수 사용 여부

 

 

수많은 옵션이 제공되고있으나 일부 옵션만 기재

 

한가지 옵션만 선택 컴파일과정을 예제로 씁니다.

Processor type and features 항목 선택 사용중인 CPU 선택

exit 두번 선택하여 엔터키를 치고 설정 저장물음에 yes합니다.

 

make menuconfig 명령으로 설정되는 커널 설정값들은 커널 소스 디렉토리의 .config 파일에 저장되므로, 특정한 설정만 변경하고자 할 떄 는 .config 파일을 vi 에디터로 열어서 수정하면 됩니다. 그러나 주의 할점은 의존성을 갖는 make menuconfig 명령을 사용하여 커널 설정값을 변경하는 것이 좋습니다.

 

커널 컴파일 - 커널 이미지 생성(Make)

커널 메뉴 설정이 완료된 후에는 make 명령을 사용하여 커널을 컴파일 합니다.

 

이 명령을 실행하게 되면 커널 이미지(bzImage)와 커널 모듈들이 컴파일 됩니다. CPU에 따라 컴파일 소요 시간이 몇 십분에서 몇 시간 정도 걸립니다. 커널 컴파일 시간을 단축하기 원한다면 -j옵션을 함께 쓰면 효과가 있습니다. -j 옵션에 프로세스 갯수를 지정해 주면 되는데, CPU가 듀얼코어 이며 하이퍼쓰레딩을 지원한다면 -j4 옵션을 사용 할 수 있습니다. -j4로 지정하여 컴파일 하는 경우 CPU모두 컴파일하는데 사용되기 때문에 다른 작업에 영향을 줄 수 있으므로 n-1 갯수로 지정해 주는 것이 좋으며, 다른 작업이 없다면 최대 프로세서 갯수로

지정해 주는 것이 컴파일 시간을 단축하는데 도움이 됩니다.

make 명령으로 오류없이 성공적으로 컴파일 작업이 완료되면 CPU 아키텍처에 따라서 경로가 조금씩 다를 수 있겠지만, 인텔 32비트 CPU

arch/i386/boot 또는 arch/x86/boot 디렉토리에, 64비트 CPU는 arch/x86_64/boot 디렉토리에 새로운 커널 이미지가 생성되며, 임베디드 타켓 보드용(ARM용)으로 컴파일한 경우에는 arch/arm/boot 디렉토리에 커널 이미지가 생성됩니다.

 

커널 모듈 설치(make modules_install)

커널 모듈은 "/lib/modules/커널버전/kernel' 디렉토리에 위치합니다. 이 디렉토리로 컴파일된 모듈들이 설치되도록

해 주는 명령이 make modules_install 입니다. make modules_install 명령을 실행하면 

새로 컴파일된 모듈들이 /lib/modules/커널버전/kernel 디렉토리에 설치됩니다.

make modules_install 명령은 컴파일된 새로운 커널과 모듈간에 의존성을 갖도록 하는 depmod -a 명령을 수행하는 역할도 함께 제공합니다. 컴파일된 커널과 모듈간에 의존성을 갖도록 하는 일반적인 명령은 다음과 같습니다.

 

depmod -ae -F system.map <커널버전>

 

예를 들으 커널 3.8.1을 컴파일 하였다면 커널과 모듈간에 다음과 같이 의존성을 부여해 줍니다.

# depmod -ae -F System.map 3.8.1

 

상기 명령을 실행하게 되면 /lib/modules/3.8.1 디렉토리에 modules.dep 이라는 의존성 데이터베이스 파일이 생성됩니다.

 

이 파일은 새로운 커널로 부팅하면 모듈 유틸리티에 의해서 모듈이 적재될 때 의존성 여부를 알려 주어 커널과 일치 하는 경우에는 모듈이 작동될 수 있도록 해 줍니다. make modules_install 명령이 실행될 때 컴파일 된 모듈 설치와 함께 depmod 명령이 실행되기 때문에 커널로 부팅 후에 의존성 오류가 나올 때는 반드시 depmod -a 명령을 실행하여 컴파일된 모듈이 커널과 의존성을 갖도록 조치해 주어야 합니다.

 

make install (커널 이미지 복사 및 initrd 이미지 생성)

커널 컴파일 작업의 마지막 과정은 컴파일된 커널 이미지를 /boot 디렉토리로 옮기는 작업입니다. 이 작업은 /boot 디렉토리로 컴파일된 이미지 파일을 복사하는 과정과 함께 initrd 이미지를 생성하는 작업을 같이해 주어야 합니다.

만일 커널 이미지만 복사하여 부트로더에서 새롭게 컴파일된 커널로 부팅되도록 설정한 후 시스템을 재시작하게 되면

커널 패닉에 빠지는 현상이 발생되므로, 반드시 initrd이미지를 다시 만들어야 함을 명심하기 바랍니다. 그러면 커널 이미지와 initrd 이미지를 /boot 디렉토리에 만드는 작업을 다음과 같이 합니다.

 

arch/x86/boot (32bit) or arch/x86_64/boot (64bit) 디렉토리에 생성된 bzlmage를 /boot 디렉토리로 복사

# cp arch/x86/boot/bzImage /boot/vmlinuz-3.8.1

 

mkinitrd 를 이용 초기 램디스크(initrd) 이미지를 생성합니다.

# mkinitrd /boot/initrd-3.8.1.img 3.8.1

 

이 2과정을 make install 명령으로 한번에 수행이 가능

# make install

 

커널 컴파일 한 번에 하기

지금까지의 커널 컴파일은 다음과 한 줄의 명령으로 모든 과정을 진행 할 수 있다.

make; make modules_install; make install

 

부트로더 설정 업데이트

/boot 디렉토리에 커널 이미지(vmlinuz-3.8.1)과 initrd 이미지(initrd-3.8.1.img)를 생성한 후에 마지막으로 해야 할 일 부트로더에 이들 이미지 정보를 등록 하는 것

 

GRUB 레거시 버전(1버전)

grub 1버전의 menu.lst 파일에 새로운 커널에 대한 부트 정보를 다음과 같은 형식으로 추가합니다.

title New Kernel (3.8.1)

root (hd0,0)

kernel /boot/vmlinuz-3.8.1 ro root=/dev/sda1

 

예) 다음과같이 수정

default=0

timeout=5

splashimage=(hd0,0)/grub/splash.xpm.gz

hiddenmenu

title SULinux Server (2.6.18-348.el5)

        root (hd0,0)

        kernel /vmlinuz-2.6.18-348.el5 ro root=/dev/VolGroup00/LogVol00 vga=771

        initrd /initrd-2.6.18-348.el5.img

title New Kernel (3.8.1)

root (hd0,0)

kernel /boot/vmlinuz-3.8.1 ro root=/dev/sda1

 

GRUB 2버전

GRUB 2버전에서는 /etc/grub.d 디렉토리에 다음 내용이 있는 06_no1.linux 스크립트를 생성하거나 40_custom 스크립트 파일에 다음 내용을 삽입

 

#!/bin/sh

set -e

echo "GRUB2 grub.cfg에 새로운 커널에 대한 부트 엔트리를 추가."

cat << EOF

menuentry "My New Kernel 3.8.1" { # 새 커널 부트 엔트리 이름을 넣어줍니다.

set root=(hd0,4)                            # 새 운영체제의 위치를 명시합니다.

linux /boot/vmlinuz-3.8.1               #새 커널명을 지정

initrd /boot/initrd-3.8.1.img             #초기 램 디스크 이미지명을 지정합니다.

}

EOF

 

그 다음 update-grub 명령을 실행하고나서 'grub2-install /dev/sda' 명령으로 부트로더를 갱신

 

시스템 재시작 및 새 커널 적용 여부 확인

시스템을 재부팅하여 새로운 커널에 대한 부트 엔트리가 보이는지 확인, 새로운 커널 부트 엔트리를 선택하여 정상인지 확인합니다.

부팅 후 uname -r 명령으로 커널 버전이 새롭게 컴파일한 버전으로 나오는지 확인 

 

앞 서 make install 명령을 실행하면 /boot 디렉토리에 커널과 initrd.img 이미지를 복사해 줄 뿐만 아니라 부트로더 설정을 새로운 부트 이미지로 자동으로 업데이트가 이뤄집니다.

주의 : 배포판마다 조금씩 차이가 있고, 기본 지원 GRUB 버전에 맞춰 동작하기에 GRUB 레거시 버전에서 2버전으로 업데이트한 경우

부트로더 설정이 업데이트 되지 않을 수 있으므로 재부팅 하기 전에 부트로더 설정 파일이 업데이트되었다는 지를 확인한 후 재부팅

make install 명령을 미사용시 부트 이미지를 /boot 디렉ㅇ토리에 만들어 준 후에 반드시 부트로더 설정을 변경한 후에 부트로더 갱신(GURB2) 해 주어야 합니다.

 

커널패치

 커널이 3.8.1-> 8.2 로 업그레이드된 경우 다시 위같은 컴파일 작업을 한다는 것은 불편합니다.

기존 버전과 새버전의 차이가 있는 부분만 기존버전에 적용하여 기존 환경되로 컴파일한다면 이상적인 작업이 될 것입니다.

그 목적으로 기존 버전의 소스와 새 버전의 소스의 차이가 있는 부분만 따로 만든 파일을 패치 라고 합니다.

 

패치법 .gz(확장자)의 패치파일일경우

gzip -cd patch -커널패치버전.gz | patch -p0

 

확장자가 없는경우

gzip -p0 < patch-커널패치버전

 

명령실행위치 : /user/src

linux 디렉토리를 패치할 경우 -p0

linux 디렉토리에 들어가서 패치할 경우 -p1

 

패치성공시 : .orig 확장자 파일 생성

실패시 : .rej 확장자 파일 생성

 

패치가 성공적으로 끝났다면 다음파일을 삭제

#find /usr/src/linux/ -name "*.orig" -exec rm -f { } |;