모듈 프로그래밍
2010. 11. 10. 21:10어느 프로그램이든지 만들려면 Makefile을 만들어야 합니다. 디바이스 드라이버도 역시 Makefile을 만들어 놓고 사용하면 편리합니다. 더욱이 커널 2.6에서는 gcc 를 이용하여 빌드하는 것이 아니기 때문에 반드시 Makefile을 만들어야 한다고 합니다.
저도 간단하게 프로그램을 작성해서 컴파일하려고 Makefile을 만들어 보았습니다.
Makefile 오류
MS-Windos에서 매우 편리한 RAPID 툴만 사용했던 저로서는 Makefile을 만들어야 한다는 것이 별로 반갑지 않습니다. 반갑지 않은 정도가 아니라 성가시고 때로는 알지 못하는 에러 때문에 고생해야 했습니다.
일반 에플리케이션을 만들기 위한 Makefile은 나름대로 큰 수정없이 사용할 수 있는 Makefile을 만들어서 사용할 정도가 되었습니다만 디바이스 드라이버를 학습하면서, 이것도 새로운 영역이라고 새로운 Makefile 형식에 사뭇 당황했습니다. 이것 또 암호문이네...으~
나름 빠르게 해본다고 책에 딸려 온 CD에 있는 소스 파일을 복사해서 main.c를 만들고 역시 CD에 있는 Makefile을 수정했습니다만 제대로 컴파일이 되질 않더군요. 가장 큰 잘못은 책에서 Makefile 부분을 대충 내용만 흝어 본 것이었습니다. 다시 책 내용을 정독하고 Makefile을 수정하고 컴파일해 보았지만 아래와 같은 에러가 계속 나더군요.
]$ make
make -C /lib/modules/2.6.9-42.0.8.ELsmp/build SUBDIRS=/home/jwjw/prjs/forum_sample/115 DeviceDriver modules
make[1]: Entering directory `/usr/src/kernels/2.6.9-42.0.8.EL-smp-i686'
make[1]: *** 타겟 `DeviceDriver'를 만들 규칙이 없음. 멈춤.
make[1]: Leaving directory `/usr/src/kernels/2.6.9-42.0.8.EL-smp-i686'
make: *** [default] 오류 2
]$ make
아~! 정말 미치겟더군요. 이런 기억이 예전에도 있었습니다. 바로 Tab 문자 때문이었죠.
그렇다면 이번에 발생한 에러는 무엇 때문일까요?
make[1]: *** 타겟 `DeviceDriver'를 만들 규칙이 없음. 멈춤.
문제는 바로 작업 디렉토리에 공백 문자가 있어서 였습니다. 공백만 없다면 한글 이름의 디렉토리 명을 사용해도 컴파일할 수가 있었습니다.
115_디바이스드라이버]$ make
make -C /lib/modules/2.6.9-42.0.8.ELsmp/build SUBDIRS=/home/jwjw/prjs/forum_sample/115_디바이스드라이버 modules
make[1]: Entering directory `/usr/src/kernels/2.6.9-42.0.8.EL-smp-i686'
CC [M] /home/jwjw/prjs/forum_sample/115_디바이스드라이버/main.o
Building modules, stage 2.
MODPOST
CC /home/jwjw/prjs/forum_sample/115_디바이스드라이버/main.mod.o
LD [M] /home/jwjw/prjs/forum_sample/115_디바이스드라이버/main.ko
make[1]: Leaving directory `/usr/src/kernels/2.6.9-42.0.8.EL-smp-i686'
115_디바이스드라이버]$
다른 프로그램 컴파일에서는 현재 디렉토리 정보가 중요하지 않았습니다만 디바이스 드라이버, 즉 모듈 프로그래밍에서는 현재의 디렉토리 명을 Makefile에 넘겨 주어야 하므로 Makefile 이 헤깔리지 않도록 디렉토리 명에 공백 문자가 있어서는 안되겠습니다.
또한 커널 별로 컴파일하는 방법이 다릅니다. 다음에 소개되는 커널별 Makefile을 참고하시기 바라며, 혹 사용하시는 시스템의 커널 버전을 확인하시려면 uname -r 을 이용하십시오.
]$ uname -r
2.6.9-42.0.8.ELsmp
]$
Makefile에 대해서는 리 눅스 디바이스 드라이버, 저자 유영창의 책 내용 중 4장 4절의 내용을 그대로 사용하면서 읽기 편하게 편집했습니다. 원저자에 누를 끼치지 않기 설명 글은 원문 그대로 가져 오지 않고 요점만 간추렸음을 말씀드립니다.
2.4 커널 외부 모듈 컴파일 용 Makefile
우선 Makefile의 전체 모습을 보시겠습니다. 예에서는 소스 파일 이름이 test.c 라고 가정하겠습니다.
KERNELDIR = /lib/modules/$(shell uname -r)/build
CFLAGS = -D__KERNEL__ -DMODULE -I$(KERNELDIR)/include -O
all: test.o
clean:
rm -rf *.o
Makefile | 설 명 |
KERNELDIR = /lib/modules/... | 모듈은 커널과 밀접하게 연관되어 있으므로 버전 문제를 방지하기 위해서는 모듈이 동작하는 커널 소스와 일치시켜야 하는데, 이를 위해 컴파일할 모듈이 참조할 커널 소스의 디렉토리를 지정한다. |
CFLAGS = -D__KERNEL__ ... | D__KERNEL__ : 커널과 관련된 내용을 활성화 하라 |
test.o | 만들어낼 오브젝트 |
clean:
rm -rf $*.o |
컴파일 결과로 생긴 모든 파일을 삭제 |
test.o 가 하나의 소스가 아니라 여러 개의 소스 파일로 만들어 진다면 아래와 같이 내용을 추가하시면 됩니다.
all: test.o
test.o : test1.o test2.o test3.o
2.6 커널 외부 모듈 컴파일 용 Makefile
2.6 커널 용은 2.4보다 조금 복잡해 보이는 듯 합니다. 프로그램 소스가 어디에 있는지도 보여 주어야 하고 말이죠. 그러다 보니 위에서 말씀드린 Makefile 오류 경험도 했습니다만 내용을 보면 모듈을 만들어 내기 위해서 2.4보다는 더욱 전문적이고 체계적으로 보입니다.
KERNELDIR = /lib/modules/$(shell uname -r)/build
obj-m := test.o
KDIR := /lib/modules/$(shell uname -r)/build
PWD := $(shell pwd)
default:
$(MAKE) -C $(KDIR) SUBDIRS=$(PWD) modules
clean:
rm -rf *.ko
rm -rf *.mod.*
rm -rf .*.cmd
rm -rf *.o
Makefile | 설 명 |
KERNELDIR = /lib/modules/... | 모듈은 커널과 밀접하게 연관되어 있으므로 버전 문제를 방지하기 위해서는 모듈이 동작하는 커널 소스와 일치시켜야 하는데, 이를 위해 컴파일할 모듈이 참조할 커널 소스의 디렉토리를 지정한다. |
obj-m := test.o | 생성할 모듈 이름 |
KDIR := /lib/modules/$(shel ... | 커널의 소스 위치 |
PWD := $(shell pwd) | 컴파일 대상 프로그램 소스 위치 |
default: $(MAKE) -C $(KDIR) ... |
모듈 컴파일 명령 |
clean: rm -rf *.ko ..... |
컴파일 결과로 생긴 모든 파일을 삭제 |
test.o 가 하나의 소스 파일로 되어 있지 않고 여러 파일로 만들어져 잇다면 아래와 같이 행을 추가하시면 됩니다.
obj-m := test.o
module-objs := test1.o test2.o test3.o
이제 컴파일해서 모듈을 만들어 내는 방법까지 알게 되었으므로 다음 시간부터는 디바이스 드라이버 프로그램에 작성에 대해 하나씩 알아 보도록 하겠습니다.
태그: *디바이스드라이버
참조: http://forum.falinux.com/zbxe/?document_srl=406210&mid=device_driver
'LVS' 카테고리의 다른 글
LVS 구축에 관한 이론 (NAT 부터 WLC 까지) (2) | 2010.12.23 |
---|---|
RR 알고리즘 개선 -> N번째 N번 부하 분산 (0) | 2010.12.20 |
커널 소켓 프로그래밍 (0) | 2010.11.20 |
ipvsadm 소스 파일 make하기 (1) | 2010.11.09 |
LVS server 구축 (2) | 2010.11.06 |
ipvsadm 소스 파일 make하기
2010. 11. 9. 00:15사이트를 접속해서 ipvsadm-1.25.tar.gz 을 받습니다.
압축을 풀어 줍니다.
압춘 폴더에 들어가 make를 실행시켜주면
[root@namyong ipvsadm-1.25]# make install
make -C libipvs
make[1]: Entering directory `/home/namyong/바탕화면/ipvsadm-1.25/libipvs'
gcc -Wall -Wunused -Wstrict-prototypes -g -fPIC -DLIBIPVS_USE_NL -DHAVE_NET_IP_VS_H -c -o libipvs.o libipvs.c
In file included from libipvs.h:13,
from libipvs.c:23:
ip_vs.h:15:29: error: netlink/netlink.h: 그런 파일이나 디렉터리가 없습니다
ip_vs.h:16:31: error: netlink/genl/genl.h: 그런 파일이나 디렉터리가 없습니다
ip_vs.h:17:31: error: netlink/genl/ctrl.h: 그런 파일이나 디렉터리가 없습니다
In file included from libipvs.h:13,
from libipvs.c:23:
같은 에러가 발생합니다.
위 에러를 해결하기 위해서는 http://www.infradead.org/~tgr/libnl/에
들어가서 libnl-2.0.tar.gz 파일을 다운로드 하여 압축을 풀어줍니다.
libnl은 netlink socket를 다루는 프로그램을 위한 라이브러리입니다.
압축이 풀린 폴더를 들어가보면 inclued/netlink/version.h.in이라는 파일이 있습니다.
그 파일의 이름을 version.h로 변경해줍니다.
그리고 include폴더를 통째로
/usr/include에 덮어쓰기를 합니다.
덮어쓸때 에러가 발생한다면 chmod 명령어를 이용해 잠깐 권한을 풀어준 후 다시 시도하면 됩니다.
덮어쓰기가 끝나면
make clean을 한후
make를 실행시키면 됩니다.
혹시 make 실행 도중 popt.h 파일 등등 기타 파일을 찾을수 없다고 나오면
chmod - R 777 /usr/include와 같이 권한을 잠시 풀어주고 다시 시도하면 해결할 수 있습니다.
'LVS' 카테고리의 다른 글
LVS 구축에 관한 이론 (NAT 부터 WLC 까지) (2) | 2010.12.23 |
---|---|
RR 알고리즘 개선 -> N번째 N번 부하 분산 (0) | 2010.12.20 |
커널 소켓 프로그래밍 (0) | 2010.11.20 |
모듈 프로그래밍 (1) | 2010.11.10 |
LVS server 구축 (2) | 2010.11.06 |
LVS server 구축
2010. 11. 6. 14:50
IP 설정 및 구축
◇LVS server(ipvsdm) : LAN1 - IP Addr : 220.70.2.xxx >> Real address
- Netmask : 255.255.255.0
- Gateway : 220.70.2.254
- DNS : 168.126.63.1
LAN2 - IP Addr : 192.168.1.1 >> Virtual address
- Netmask : 255.255.255.0
◇Real Server1 : IP Addr : 192.168.1.2
Netmask : 255.255.255.0
Gateway : 192.168.1.1
DNS : 192.168.1.1
◇Real Server2 : IP Addr : 192.168.1.3
Netmask : 255.255.255.0
Gateway : 192.168.1.1
DNS : 192.168.1.1
LVS Server 설정
◇ipvsadm 설치
# yum -y install ipvsadm
◇동작확인
# ipvsadm
IP Virtual Server version 1.2.1 (size=4096)
ProtProt LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port Forward Weight ActiveConn InActConn
◇시스템을 통해 다른 시스템으로패킷이 포워딩 될수 있도록 수정
# vi /etc/sysctl.conf
net.ipv4.ip_forward=1
-> 적용
# sysctl -p
◇ipvsadm 구동
# service ipvsadm start
◇ipvsadm 설정
# ipvsadm -A -t 220.70.2.xxx:80 -s rr
# ipvsadm -a -t 220.70.2.xxx:80 -r 192.168.1.2:80 -m
# ipvsadm -a -t 220.70.2.xxx:80 -r 192.168.1.3:80 -m
SELinux disabled :
#vim /etc/selinux/config
line#7 SELINUX=enforcing -->> SELINUX=disabled 로 수정
◇ipvsadm 설정 확인
# ipvsadm -L
IP Virtual Server version 1.2.11.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port Forward Weight ActiveConn InActConn
TCP 220.70.2.x:http rr
-> 192.168.1.2:http Route 1 0 0
-> 192.168.1.3:http Route 1 0 0
REAL Server 설정
◇server 페이지 만들기
# vim /var/www/html/index.html
<내용 입력, 저장 후 종료(wq)>
◇ server 구동
# service httpd start
1. ipvsadm의 기본 문법
- 서비스
ipvsadm [명령] [프로토콜 옵션] [서비스] [스케줄링 방법] [세션유지 옵션]
- 리얼서버
ipvsadm [명령] [프로토콜 옵션] [서비스] -r [리얼서버 옵션] [가중치 옵션]
서비스/리얼서버 관련 >명령<
-A : 서비스 추가
-E : 서비스 수정
-D : 서비스 삭제
-a : 리얼서버 추가
-e : 리얼서버 수정
-d : 리얼서버 삭제
>프로토콜<
-t TCP
-u UDP
-f firewall 서비스 추가(NAT 방식에서 사용)
기타
-s [ rr | wrr | lc | wlc | lblc | lblcr | dh | sh | sed | nq ] : 스케줄링 방법을 설정한다.
-p [timeout]: 세션 타임아웃 설정
-r [서버주소:서비스포트] : 리얼서버를 설정한다.
-w [가중치] : 가중치를 설정한다.
설정 확인
-L : 서비스/리얼서버 리스트를 출력한다.
-n : 숫자형식(호스트네임->아이피주소)로 출력한다.
-c : 현재 연결을 출력한다.
입/출력
-S : 표준출력(화면프린트)으로 현재 설정을 내보낸다.
-R : 표준입력을 통해 설정을 가져온다
2. 스케줄링 방식 정리(rr,wrr,lc,wlc)
ipvsadm에서 지원하는 스케줄링 방식은 총 8개가 있지만 이 문서에서는 네개의 방식만 정리.
(1) rr
round-robin방식은 가장 기본적인 스케줄링 방식으로 "순차적으로" 작업을 각각의 노드에 분배하는 방식이다. 만약 3 대의 노드(A,B,C)에 round robin 방식을 사용하면, A->B->C->A->B->C와 같이 실행이 된다.
(2) wrr
노드별로 가중치를 설정하여 작업을 순차적으로 분배하는 방식으로 여러대의 서버가 각각 성능이 다른경우 성능에 맞춰 가중치를 설정해 주면 성능이 낮은 서버에 과도한 부하가 걸리는 것을 방지할 수 있다.
(3) lc
"현재 활성화 되어있는(ESTABLISHED)" 접속량이 적은 서버부터 작업을 할당하는 방식으로, 불필요한 유휴자원이 발생하는 것을 막을 수 있다. 만약 접속이 오래 유지되지 않는 경우(http) 이 방식을 사용하면, A->A->A->A->...와 같이 리스트 위쪽에 있는 노드 위주로 작업이 할당된다.
(4) wlc
노드별로 가중치를 설정하여 접속량이 적은 서버부터 작업을 할당하는 방식으로 lc보다 효율적인 자원분배가 가능하다.
3. 타임아웃
(1)세션 타임아웃
ipvsadm에서 -p 옵션을 이용하여 어떤 서비스에 세션 타임아웃 시간을 설정하면, 한번 세션이 열린후 타임아웃 시간 내에 동일한 주소에서 세션이 다시 열렸을 때 처음에 접속했던 RIP로 접속이 된다.
(2)Idle 타임아웃
ipvsadm --set옵션을 이용하면 프로토콜의 Idle timeout 시간을 설정할 수 있다. timeout 시간이 지나면 연결이 끊어지게 된다. 예를 들어,
ivpsadm --set 10 20 30
로 설정을 해 주게 되고 ftp연결후 10초간 아무것도 하지 않으면 연결이 끊어진다. 이는 http와 같이 한번 보내면 해당 연결이 끊겨도 별 문제가 없는 서비스의 경우는 상관없지만, ftp, nfs와 같은 서비스를 사용할 때에는 신중하게 값을 설정해야 한다.
'LVS' 카테고리의 다른 글
LVS 구축에 관한 이론 (NAT 부터 WLC 까지) (2) | 2010.12.23 |
---|---|
RR 알고리즘 개선 -> N번째 N번 부하 분산 (0) | 2010.12.20 |
커널 소켓 프로그래밍 (0) | 2010.11.20 |
모듈 프로그래밍 (1) | 2010.11.10 |
ipvsadm 소스 파일 make하기 (1) | 2010.11.09 |