우분투 커널 컴파일 및 모듈 프로그래밍 문제

sesise의 이미지

안녕하세요
리눅스 커널 컴파일 및 모듈 프로그래밍을 하다가 막혀서
이것 저것 찾아보았지만 도저히 해결할 방법을 찾지
못해서 글을 올리게 되었습니다.

우선 제가 하고자 하는 것은 커널에서 IP 패킷이 오가는 부분을
변경해서, 특정 모듈에 정의된 함수를 실행 시키는 것입니다.

그래서 제가 한 것은 우선 net/core/dev.c 파일을 수정했습니다.

int (*flow_gen_xmit)(struct sk_buff *)=0;       /* new */
 
int dev_queue_xmit(struct sk_buff *skb)
{
        struct net_device *dev = skb->dev;
        struct Qdisc *q;
        int rc = -ENOMEM;
 
        if (flow_gen_xmit&& (*flow_gen_xmit)(skb)) {    /* new */
                kfree_skb(skb);                         /* new */
                printk(KERN_INFO "flow_gen_xmit");      /* new */
                return 0;                               /* new */
        }                                               /* new */
...
EXPORT_SYMBOL_NOVERS(flow_gen_xmit); /* new */

위 코드에서 보시는 바와 같이 flow_gen_xmit 이라는 함수 포인터를 선언하고
일단은 NULL로 두었습니다. 그 후 dev_queue_xmit 함수 내에 flow_gen_xmit
함수 포인터가 모듈에서 정의한 함수를 가리키고 있다면, 그 함수를 호출하도록
만들었습니다. 그리고 EXPORT_SYMBOL_NOVERS를 해주어서 커널 외부에서도
참조할 수 있도록 했습니다.

이렇게 변경한 커널을 가지고
fakeroot make-kpkg --initrd --append-to-version=-some-string-here kernel-image kernel-headers
명령으로 커널을 컴파일 했고, 생성된 패키지로 커널을 설치하고 재부팅하여 새로 컴파일한 커널로
부팅을 완료하였습니다. cat /proc/kallsyms 를 해보면 위에서 제가 EXPORT한 flow_gen_xmit을
발견할 수 있었습니다.
한가지 이상한 점은 커널을 컴파일할 때 다음과 같은 warning이 발생합니다.

net/core/dev.c:4491: warning: data definition has no type or storage class
net/core/dev.c:4491: warning: type defaults to ‘int’ in declaration of ‘EXPORT_SYMBOL_NOVERS’
net/core/dev.c:4491: warning: parameter names (without types) in function declaration

그리고 이렇게 새로 컴파일한 커널을 활용하기 위하여 다음과 같은 모듈 프로그램을 작성했습니다.

#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/skbuff.h>
#include <linux/ip.h>
#include <linux/sysctl.h>
#include <linux/unistd.h>
 
MODULE_LICENSE("GPL");
 
extern void *sys_call_table[];
extern int (*flow_gen_xmit)(struct sk_buff *);
 
int packet_dropper(struct sk_buff *skb) {
	printk("packet dropper\n");
	return 0;
}
 
static int __init flow_gen_init(void) {
	flow_gen_xmit = packet_dropper;
	printk("<1> packet_dropper: now dropping pakcets\n");
	return 0;
}
 
static void __exit flow_gen_exit(void) {
	flow_gen_xmit = 0;
	printk("<1> packet_dropper: uninstalled\n");
}
 
module_init(flow_gen_init);
module_exit(flow_gen_exit)

이 모듈 프로그램은 packet_dropper라는 함수를 정의하고 init_module에서 커널에서
정의한 flow_gen_xmit이 packet_dropper를 가리키게 하여, dev_queue_xmit 함수가
호출될 때 마다 packet_dropper라는 함수가 호출되도록 하는 것입니다.

이 모듈을 컴파일하기 위한 Makefile은 다음과 같습니다.

obj-m    := flow_gen.o
 
KDIR    := /lib/modules/$(shell uname -r)/build
PWD    := $(shell pwd)
 
all:
	$(MAKE) -C $(KDIR) M=$(PWD) modules
clean:
	$(MAKE) -C $(KDIR) M=$(PWD) clean

이 Makefile을 이용하여 make 를 해보면 다음과 같은 warning이 뜹니다.
WARNING: "flow_gen_xmit" [/home/sesise/aos/flow_gen.ko] undefined!
하지만 어쨌든 컴파일은 완료됩니다.

컴파일하여 생성된 ko 파일을 insmod하면 다음과 같은 에러 메시지가 발생합니다.
insmod: error inserting 'flow_gen.ko': -1 Unknown symbol in module

이 에러 메시지를 가지고 구글링하여 이것 저것 찾아본 후 커널 2.6부터는 sys_call_table을
명시적으로 EXPORT 해주어야 한다고 해서 arc/x86/kernel/i386_ksyms_32.c 파일에
다음을 추가해 주었습니다.

커널 소스중 ./x86/kernel/i386_ksyms_32.c 에서 
 
extern void *sys_call_table; 
EXPORT_SYMBOL(sys_call_table); 

이렇게 하고 다시 커널을 컴파일하고 insmod를 해 보았지만 똑같은 에러 메시지가 발생하고 있습니다.

질문이 많이 길어졌습니다. 요약하자면, 커널의 net/core/dev.c 에서 함수 포인터를 하나 설정하고
flow_gen 모듈이 커널에 load되었을 경우에만 커널에 생성한 함수 포인터에 특정 함수를 지정하여
dev_queue_xmit 함수가 호출될 때마다, 제가 정의한 함수를 호출되게 하고 싶은데, Unknown symbol
에러가 발생한다는 것입니다.

저의 개발 환경은 VMware Workstation 6.5에 우분투 8.04.2를 설치했습니다.
커널의 버전은 2.6.24-24-generic 입니다.

답변에 미리 감사드립니다. 좋은 하루되세요~ ^^

댓글 달기

Filtered HTML

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

BBCode

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param>
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

Textile

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • You can use Textile markup to format text.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Markdown

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • Quick Tips:
    • Two or more spaces at a line's end = Line break
    • Double returns = Paragraph
    • *Single asterisks* or _single underscores_ = Emphasis
    • **Double** or __double__ = Strong
    • This is [a link](http://the.link.example.com "The optional title text")
    For complete details on the Markdown syntax, see the Markdown documentation and Markdown Extra documentation for tables, footnotes, and more.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Plain text

  • HTML 태그를 사용할 수 없습니다.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 줄과 단락은 자동으로 분리됩니다.
댓글 첨부 파일
이 댓글에 이미지나 파일을 업로드 합니다.
파일 크기는 8 MB보다 작아야 합니다.
허용할 파일 형식: txt pdf doc xls gif jpg jpeg mp3 png rar zip.
CAPTCHA
이것은 자동으로 스팸을 올리는 것을 막기 위해서 제공됩니다.