Section 25.3. Objective 3: Patching a Kernel


25.3. Objective 3: Patching a Kernel

When you start patching and customizing kernels, it becomes vital to make it obvious which source tree contains which patches and exactly what special functionality is in the currently running kernel. You should use directory names and other means to actively indicate these things.

25.3.1. Applying the Patch

Once your desired patch has been located and fetched, you can start building a new kernel with it. In the following example, you will install a new kernel patch to take your kernel from 2.4.23 to 2.4.24. After fetching it, a good place to store it is /usr/src/patch-2.4.24.bz2.

  1. Copy your unpatched source tree to a tree that you're going to patch. Choose a target directory name that reflects the capabilities of the patched kernel. If this is going to be a symmetric multiprocessing (SMP) kernel, linux-2.4.24-SMP might be most appropriate:

     cp -a linux-2.4.23 linux-2.4.24-SMP 

  2. Inspect your patch, using bzmore for a bz2 file, to see what path it operates on. This one starts modifying linux-2.4.24/Makefile. The directory name does not match the one you've chosen earlier, and this must be corrected in the next two steps. The top of the patch file is shown here:

     # diff -urN linux-2.4.23/Makefile linux-2.4.24/Makefile --- linux-2.4.23/Makefile       2003-11-28 10:26:21.000000000 -0800 +++ linux-2.4.24/Makefile       2004-01-05 05:53:56.000000000 -0800 @@ -1,6 +1,6 @@  VERSION = 2  PATCHLEVEL = 4 

  3. Change to the top-level of the source tree:

     # cd linux-2.4.24-SMP 

  4. Apply the patch:

     # bzip2 -dc ../patch-2.4.24.bz2 | patch -p1 patching file Makefile patching file arch/cris/drivers/ds1302.c patching file arch/cris/drivers/pcf8563.c patching file arch/m68k/bvme6000/rtc.c ... 

    The -p1 option to patch instructs it to remove one level of path from the front of the filenames in the patch. In this case, it removes the leading linux-2.4.24 and leaves Makefile, which is the correct path considering the directory you're standing in. Thus, the option corrects for the directory name mismatch in the path. patch reads patch files from its standard input, so it must always be fed by a pipe or an input redirect (the < shell metacharacter).

  5. Now you must reconcile any rejected chunks in the patch. Any rejected chunks are saved into .rej files, which are clearly shown in the run. In case the output from patch is overwhelming, the files can easily be found with a find command such as find . -name '*.rej'.

    These rejected patch chunks must be applied by hand. By this we mean that you must take out your favorite editor and look at the .rej file alongside the file it failed to patch. If a patch to orinoco.c failed, the corresponding reject file is orinoco.c.rej. Such a file is shown next:

     *************** *** 4160,4168 ****         /* Setup / override net_device fields */         dev->init = orinoco_init;         dev->hard_start_xmit = orinoco_xmit; - #ifdef SET_MAC_ADDRESS -         dev->set_mac_address = orinoco_set_mac_address; - #endif        /* SET_MAC_ADDRESS */         dev->tx_timeout = orinoco_tx_timeout;         dev->watchdog_timeo = HZ; /* 1 second timeout */         dev->get_stats = orinoco_get_stats; --- 3947,3952 ----         /* Setup / override net_device fields */         dev->init = orinoco_init;         dev->hard_start_xmit = orinoco_xmit;         dev->tx_timeout = orinoco_tx_timeout;         dev->watchdog_timeo = HZ; /* 1 second timeout */         dev->get_stats = orinoco_get_stats; 

    The lines marked with a hyphen should be removed from orinoco.c. Any lines marked with a plus sign are to be inserted. The numbers on top are the approximate line numbers; these can be very approximate, especially if you're applying a third-party patch.

    Reasons for patches being rejected could be that the line numbers are too far off or that the lines cannot be matched exactly. As a human, you can do more intelligent string matching and line searching than patch can do.

  6. If you are going to give this patched kernel a special name reflecting its special capabilities, edit the top-level Makefile. If you're going to build an SMP kernel, for example, you can add that as follows. If you're simply applying a kernel patch, the patch updates the SUBLEVEL itself.

     VERSION = 2 PATCHLEVEL = 4 SUBLEVEL = 24 EXTRAVERSION = -SMP 

    Note that the directory the modules will be installed in will be named /lib/modules/2.4.24-SMP and that the System.map file must be called /boot/System.map-2.4.24-SMP after this. The uname -r will also show the version to be 2.4.24-SMP.

  7. Update the kernel configuration. The easiest way is to run make oldconfig, which will reapply the configuration already in the source tree and ask you about any new kernel options. If you prefer, you can instead use your favorite of the config, menuconfig or xconfig methods.

  8. Now build and install the kernel through the make commands discussed earlier.

25.3.2. Removing a Patch

You should not ordinarily need to remove a patch, because you should have backups of your kernel source without the patches you apply. But sometimes the kernel sources just take too much space, and sometimes you have worked, say, three different patches into the kernel and then want to reverse just one. Removing the 2.4.24 patch applied earlier is a simple matter of running patch in reverse with -R as shown in the following listing:

 # bzip2 -dc ../patch-2.4.24.bz2 | patch -p1 -R patching file Makefile patching file arch/cris/drivers/ds1302.c patching file arch/cris/drivers/pcf8563.c patching file arch/m68k/bvme6000/rtc.c ... 

When reversing a patch, you may also get rejects, so check for them and resolve them. It is also worth mentioning that patch understands enough of what it does that it may well deduce that you meant to use -R, as shown in the following command:

 # bzip2 -dc ../patch-2.4.24.bz2 | patch -p1 patching file MakefileReversed (or previously applied) patch detected!  Assume -R? [n] 

In that case, if you know that patch is right, just answer y. If you ever get this message while applying a patch, you should take a look at the patch before answering either way. It may be that the patch producer reversed the order of the old and new files on his command line and produced a reversed patch. It may also be that the patch includes a patch you have already applied. Then it will look as if the patch is reversed because patch material is already present in your sources. But the patch is not reversed, it only has redundant parts that will fail to apply. It is usually very easy to see if a patch is reversed. If you look at the first few lines of the following patch, they should give clues:

 Index: linux-2.4.23/arch/alpha/defconfig =================================================================== --- linux-2.4.23.orig/arch/alpha/defconfig      2003-12-15 15:06:57.853807752 +0 100 +++ linux-2.4.23/arch/alpha/defconfig   2003-12-15 15:06:58.497669693 +0100 @@ -1,6 +1,9 @@  # 

The first filename given, marked ---, has a path that contains .orig, a good clue that this is the original source file. The second line, marked +++, has nothing specific in its path and thus seems likely to be the modified tree. The old file is supposed to be first and the modified second, so this patch is probably not reversed.



LPI Linux Certification in a Nutshell
LPI Linux Certification in a Nutshell (In a Nutshell (OReilly))
ISBN: 0596005288
EAN: 2147483647
Year: 2004
Pages: 257

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net