Sophie

Sophie

distrib > Mageia > 7 > armv7hl > media > core-release > by-pkgid > 265a7483afc48e27c236b36e810be507 > files > 52

lkmpg-1.1.0-23.mga7.noarch.rpm

<HTML
><HEAD
><TITLE
>Compiling Kernel Modules</TITLE
><META
NAME="GENERATOR"
CONTENT="Modular DocBook HTML Stylesheet Version 1.7"><LINK
REL="HOME"
TITLE="The Linux Kernel Module Programming Guide"
HREF="book1.htm"><LINK
REL="UP"
TITLE="Hello World"
HREF="c147.htm"><LINK
REL="PREVIOUS"
TITLE="Hello World"
HREF="c147.htm"><LINK
REL="NEXT"
TITLE="Hello World (part 2)"
HREF="x257.htm"></HEAD
><BODY
CLASS="SECT1"
BGCOLOR="#FFFFFF"
TEXT="#000000"
LINK="#0000FF"
VLINK="#840084"
ALINK="#0000FF"
><DIV
CLASS="NAVHEADER"
><TABLE
SUMMARY="Header navigation table"
WIDTH="100%"
BORDER="0"
CELLPADDING="0"
CELLSPACING="0"
><TR
><TH
COLSPAN="3"
ALIGN="center"
>The Linux Kernel Module Programming Guide</TH
></TR
><TR
><TD
WIDTH="10%"
ALIGN="left"
VALIGN="bottom"
><A
HREF="c147.htm"
ACCESSKEY="P"
>Prev</A
></TD
><TD
WIDTH="80%"
ALIGN="center"
VALIGN="bottom"
>Chapter 2. Hello World</TD
><TD
WIDTH="10%"
ALIGN="right"
VALIGN="bottom"
><A
HREF="x257.htm"
ACCESSKEY="N"
>Next</A
></TD
></TR
></TABLE
><HR
ALIGN="LEFT"
WIDTH="100%"></DIV
><DIV
CLASS="SECT1"
><H1
CLASS="SECT1"
><A
NAME="AEN208"
></A
>Compiling Kernel Modules</H1
><A
NAME="AEN210"
></A
><P
>Kernel modules need to be compiled with certain gcc options to make them work.  In addition, they also need to be
	compiled with certain symbols defined.  This is because the kernel header files need to behave differently, depending on
	whether we're compiling a kernel module or an executable.  You can define symbols using gcc's <TT
CLASS="OPTION"
>-D</TT
> option, or
	with the <TT
CLASS="LITERAL"
>#define</TT
> preprocessor command.  We'll cover what you need to do in order to compile kernel modules
	in this section.</P
><P
></P
><UL
><LI
><P
><TT
CLASS="OPTION"
>-c</TT
>:
		A kernel module is not an independant executable, but an object file which will be linked into the kernel during runtime
		using insmod.  As a result, modules should be compiled with the <TT
CLASS="OPTION"
>-c</TT
> flag.</P
></LI
><LI
><P
><TT
CLASS="OPTION"
>-O2</TT
>:
		The kernel makes extensive use of inline functions, so modules must be compiled with the optimization flag turned
		on.  Without optimization, some of the assembler macros calls will be mistaken by the compiler for function calls.  This
		will cause loading the module to fail, since insmod won't find those functions in the kernel.</P
></LI
><LI
><P
><TT
CLASS="OPTION"
>-W -Wall</TT
>:
		A programming mistake can take take your system down.  You should always turn on compiler warnings, and this applies to
		all your compiling endeavors, not just module compilation.</P
></LI
><LI
><P
><TT
CLASS="OPTION"
>-isystem /lib/modules/`uname -r`/build/include</TT
>:
		You must use the kernel headers of the kernel you're compiling against.  Using the default <TT
CLASS="FILENAME"
>/usr/include/linux</TT
> won't work.</P
></LI
><LI
><P
><TT
CLASS="VARNAME"
>-D__KERNEL__</TT
>: Defining this symbol tells the header files that the code will be run in
		kernel mode, not as a user process.</P
></LI
><LI
><P
><TT
CLASS="VARNAME"
>-DMODULE</TT
>: This symbol tells the header files to give the appropriate definitions for a
		kernel module.</P
></LI
></UL
><P
>We use gcc's <TT
CLASS="OPTION"
>-isystem</TT
> option instead of <TT
CLASS="OPTION"
>-I</TT
> because it tells gcc to surpress some
	"unused variable" warnings that <TT
CLASS="OPTION"
>-W -Wall</TT
> causes when you include <TT
CLASS="FILENAME"
>module.h</TT
>.
	By using <TT
CLASS="OPTION"
>-isystem</TT
> under gcc-3.0, the kernel header files are treated specially, and the warnings are
	surpressed.  If you instead use <TT
CLASS="OPTION"
>-I</TT
> (or even <TT
CLASS="OPTION"
>-isystem</TT
> under gcc 2.9x), the "unused variable"
	warnings will be printed.  Just ignore them if they do.</P
><P
>So, let's look at a simple Makefile for compiling a module named <TT
CLASS="FILENAME"
>hello-1.c</TT
>:</P
><DIV
CLASS="EXAMPLE"
><A
NAME="AEN246"
></A
><P
><B
>Example 2-2. Makefile for a basic kernel module</B
></P
><PRE
CLASS="SCREEN"
>TARGET  := hello-1
WARN    := -W -Wall -Wstrict-prototypes -Wmissing-prototypes
INCLUDE := -isystem /lib/modules/`uname -r`/build/include
CFLAGS  := -O2 -DMODULE -D__KERNEL__ ${WARN} ${INCLUDE}
CC      := gcc-3.0
	
${TARGET}.o: ${TARGET}.c

.PHONY: clean

clean:
    rm -rf ${TARGET}.o</PRE
></DIV
><P
>As an exercise to the reader, compile <TT
CLASS="FILENAME"
>hello-1.c</TT
> and insert it into the kernel with <B
CLASS="COMMAND"
>insmod
	./hello-1.o</B
> (ignore anything you see about tainted kernels; we'll cover that shortly).  Neat, eh?  All modules
	loaded into the kernel are listed in <TT
CLASS="FILENAME"
>/proc/modules</TT
>.  Go ahead and cat that file to see that your module
	is really a part of the kernel.  Congratulations, you are now the author of Linux kernel code!  When the novelty wares off,
	remove your module from the kernel by using <B
CLASS="COMMAND"
>rmmod hello-1</B
>.  Take a look at
	<TT
CLASS="FILENAME"
>/var/log/messages</TT
> just to see that it got logged to your system logfile.</P
><P
>Here's another exercise to the reader.  See that comment above the return statement in
	<TT
CLASS="FUNCTION"
>init_module()</TT
>?  Change the return value to something non-zero, recompile and load the module again.  What
	happens?</P
></DIV
><DIV
CLASS="NAVFOOTER"
><HR
ALIGN="LEFT"
WIDTH="100%"><TABLE
SUMMARY="Footer navigation table"
WIDTH="100%"
BORDER="0"
CELLPADDING="0"
CELLSPACING="0"
><TR
><TD
WIDTH="33%"
ALIGN="left"
VALIGN="top"
><A
HREF="c147.htm"
ACCESSKEY="P"
>Prev</A
></TD
><TD
WIDTH="34%"
ALIGN="center"
VALIGN="top"
><A
HREF="book1.htm"
ACCESSKEY="H"
>Home</A
></TD
><TD
WIDTH="33%"
ALIGN="right"
VALIGN="top"
><A
HREF="x257.htm"
ACCESSKEY="N"
>Next</A
></TD
></TR
><TR
><TD
WIDTH="33%"
ALIGN="left"
VALIGN="top"
>Hello World</TD
><TD
WIDTH="34%"
ALIGN="center"
VALIGN="top"
><A
HREF="c147.htm"
ACCESSKEY="U"
>Up</A
></TD
><TD
WIDTH="33%"
ALIGN="right"
VALIGN="top"
>Hello World (part 2)</TD
></TR
></TABLE
></DIV
></BODY
></HTML
>