How to create and use a patch in Linux
Updated March 17,
2003
Created November 19, 2001
Autogenerated Site
Map
Search this Site!:
Creating a Patch File:
diff -Naur olddir newdir > new-patch
- or
-
diff -Naur oldfile newfile >new-paatch
A Note concerning Patch and the number of Directory Levels used:
Try to
make sure when creating a patchfile that you have the same number of directories
levels for both the olddir path and newdir path. For Ex: --- old/modules/pcitable Mon Sep 27 11:03:56 1999
+++ new/modules/pcitable Tue Dec 19 20:05:41 2000
The above diff would work ok as a patch. --- old/try1/other/modules/pcitable Mon Sep 27 11:03:56 1999
+++ new/modules/pcitable Tue Dec 19 20:05:41 2000
You may have problems with the above diff working as a patch. Note that
the first one has 4 directory levels mentioned and the 2nd one has only two. I
would suggest modifying the --- and +++ lines to make the directory structure in
both to be the same number of levels deep.
Using the Patch Command:
patch -p0 <new-patch
patch -p1 <new-patch
Which one of the above patch commands you use depends on your current
working directory.
Other Methods for calling the patch command - using
standard input of patch: cat new-patch | patch -p0
Other methods for calling the patch command - using a "here document": patch -p0 << EOF
--- old/modules/pcitable Mon Sep 27 11:03::56 1999
+++ new/modules/pcitable Tue Dec 19 20:05:41 2000
@@ -1,4 +1,6 @@
0x0e11 0xae10 "cpqarray" "Compaq|Smart-2/P RAID Controller"
+0x1000 0x0010 "cpqarray" "Compaq|Integrated Array Controller"
+0x1011 0x0046 "cpqarray" "Compaq|Smart-2/P RAID Controller"
0x0e11 0xae32 "tlan" "Compaq|Netelligent 10/100"
0x0e11 0xae34 "tlan" "Compaq|Netelligent 10"
0x0e11 0xae35 "tlan" "Compaq|Integrated NetFlex-3/P"
@@ -21,6 +23,7 @@
0x1000 0x000f "ncr53c8xx" "Symbios|53c875"
0x1000 0x0012 "ncr53c8xx" "Symbios|53c895a"
0x1000 0x008f "ncr53c8xx" "Symbios|53c875J"
+0x1000 0x000a "sym53c8xx" "Symbios|53c1510"
0x1000 0x0701 "yellowfin" "Symbios|83C885 gigabit ethernet"
0x1000 0x0702 "yellowfin" "Symbios|Yellowfin G-NIC gigabit ethernet"
0x1011 0x0001 "tulip" "DEC|DECchip 21050"
--- old/usr/share/kudzu/pcitable Sun Sep 226 17:11:23 1999
+++ new/usr/share/kudzu/pcitable Tue Dec 19 20:05:41 2000
@@ -15,6 +15,8 @@
0x0e11 0x3034 "unknown" "Compaq|QVision 1280/p"
0x0e11 0x4000 "unknown" "Compaq|4000 [Triflex]"
0x0e11 0xa0f3 "ignore" "Compaq|Triflex PCI to ISA Bridge"
+0x1000 0x0010 "cpqarray" "Compaq|Integrated Array Controller"
+0x1011 0x0046 "cpqarray" "Compaq|Smart-2/P RAID Controller"
0x0e11 0xae10 "cpqarray" "Compaq|Smart-2/P RAID Controller"
0x0e11 0xae29 "unknown" "Compaq|MIS-L"
0x0e11 0xae2a "unknown" "Compaq|MPC"
@@ -46,6 +48,7 @@
0x1000 0x000f "ncr53c8xx" "Symbios|53c875"
0x1000 0x0012 "ncr53c8xx" "Symbios|53c895a"
0x1000 0x008f "ncr53c8xx" "Symbios|53c875J"
+0x1000 0x000a "sym53c8xx" "Symbios|53c1510"
0x1000 0x0701 "yellowfin" "Symbios|83C885 gigabit ethernet"
0x1000 0x0702 "yellowfin" "Symbios|Yellowfin G-NIC gigabit ethernet"
0x1000 0x0901 "unknown" "Symbios|61C102"
EOF
For the "here document", patch will read all the following lines, up until
it reaches the delimeter that we specified after the << symbol. The
delimeter we choose must appear at the beginning of a line, and must appear
alone. In our case we are using the delimeter EOF. EOF has no special meaning,
other than the fact that it is not likely that we would have a reason to type
EOF at the beginning of any given line.
For more information on here
documents click here: heredoc.html
Levels in the Patch Command (-p0 or -p1?):
The -p option will optionally
strip off directory levels from the patchfile. For Ex: if you have a patchfile
with a header as such: --- old/modules/pcitable Mon Sep 27 11:03:56 1999
+++ new/modules/pcitable Tue Dec 19 20:05:41 2000
Using a -p0 will expect, from your current working directory, to find a
subdirectory called "new", then "modules" below that, then the "pcitable" file
below that.
Using a -p1 will strip off the 1st level from the path and
will expect to find (from your current working directory) a directory called
"modules", then a file called "pcitable". Patch will ignore the "new" directory
mentioned in the header of the patchfile.
Using a -p2 will strip of the
first two levels from the path. Patch will expect to find "pcitable" in the
current working directory. Patch will ignore the "new" and "modules" directories
mentioned in the header of the patchfile.
Using a -p3 in this example
would not be a good thing. Patch probably wouldn't patch
anything.
...
Applying a Patch:
Just change to the correct directory and give the
patch command (see Using the
Patch Command above). Usually is: cd /usr/src/linux
patch -p0 <new-patch
unless the patchfile has "linux" as part of the directory structure on the
+++ line, in that case issue the patch command with the -p1 as follows: patch -p1 <new-patch
Patch Header:
In these examples a patch header begins with the two lines
that begin with a --- and +++. This would indicate which filename to begin
processing.
Multiple Patches in a Patchfile:
A patchfile can have multiple sections,
each beginning with the --- / +++ headers mentioned above. So a single patchfile
can actually modify several files. If you are reviewing a patchfile be sure to
search for every instance of --- throughout the patchfile to see all the
different files it patches.
An Example of one method to browse a patchfile:
less /tmp/file-patch <ENTER>
/--- <ENTER>
n
n
n
Note that the "/" invokes the search function in less, and each time you
press "n" less will search for the next matching searchstring.
Hunks:
A hunk is a section to be patched. A hunk usually begins and ends
with lines that don't need any changes, they are just mentioned so that Patch
can find the appropriate place in the files to be patched. Hunk in these
examples begins with a double at symbol (@@) and ends when either a new hunk
starts or it finds a new patch header. Here's an example of a hunk: @@ -1,4 +1,6 @@
0x0e11 0xae10 "cpqarray" "Compaq|Smart-2/P RAID Controller"
+0x1000 0x0010 "cpqarray" "Compaq|Integrated Array Controller"
+0x1011 0x0046 "cpqarray" "Compaq|Smart-2/P RAID Controller"
0x0e11 0xae32 "tlan" "Compaq|Netelligent 10/100"
0x0e11 0xae34 "tlan" "Compaq|Netelligent 10"
0x0e11 0xae35 "tlan" "Compaq|Integrated NetFlex-3/P"
Indentation in a Hunk:
In these examples you will notice that each hunk
has been indented so that the text does not occupy the first column. In these
examples Patch uses the first column in each patch to list the lines to be added
or removed.
The First Column of a Hunk (+, -, and a blank):
The + would indicate
that this particular line is to be added.
The - would indicate that this
particular line is to be removed.
A line with neither a plus or minus
would indicate that this particular line of code is just a reference
point.
An Example Patchfile:
diff -u old/modules/pcitable new/modules/pcitable
--- old/modules/pcitable Mon Sep 27 11:03::56 1999
+++ new/modules/pcitable Tue Dec 19 20:05:41 2000
@@ -1,4 +1,6 @@
0x0e11 0xae10 "cpqarray" "Compaq|Smart-2/P RAID Controller"
+0x1000 0x0010 "cpqarray" "Compaq|Integrated Array Controller"
+0x1011 0x0046 "cpqarray" "Compaq|Smart-2/P RAID Controller"
0x0e11 0xae32 "tlan" "Compaq|Netelligent 10/100"
0x0e11 0xae34 "tlan" "Compaq|Netelligent 10"
0x0e11 0xae35 "tlan" "Compaq|Integrated NetFlex-3/P"
@@ -21,6 +23,7 @@
0x1000 0x000f "ncr53c8xx" "Symbios|53c875"
0x1000 0x0012 "ncr53c8xx" "Symbios|53c895a"
0x1000 0x008f "ncr53c8xx" "Symbios|53c875J"
+0x1000 0x000a "sym53c8xx" "Symbios|53c1510"
0x1000 0x0701 "yellowfin" "Symbios|83C885 gigabit ethernet"
0x1000 0x0702 "yellowfin" "Symbios|Yellowfin G-NIC gigabit ethernet"
0x1011 0x0001 "tulip" "DEC|DECchip 21050"
--- old/usr/share/kudzu/pcitable Sun Sep 226 17:11:23 1999
+++ new/usr/share/kudzu/pcitable Tue Dec 19 20:05:41 2000
@@ -15,6 +15,8 @@
0x0e11 0x3034 "unknown" "Compaq|QVision 1280/p"
0x0e11 0x4000 "unknown" "Compaq|4000 [Triflex]"
0x0e11 0xa0f3 "ignore" "Compaq|Triflex PCI to ISA Bridge"
+0x1000 0x0010 "cpqarray" "Compaq|Integrated Array Controller"
+0x1011 0x0046 "cpqarray" "Compaq|Smart-2/P RAID Controller"
0x0e11 0xae10 "cpqarray" "Compaq|Smart-2/P RAID Controller"
0x0e11 0xae29 "unknown" "Compaq|MIS-L"
0x0e11 0xae2a "unknown" "Compaq|MPC"
@@ -46,6 +48,7 @@
0x1000 0x000f "ncr53c8xx" "Symbios|53c875"
0x1000 0x0012 "ncr53c8xx" "Symbios|53c895a"
0x1000 0x008f "ncr53c8xx" "Symbios|53c875J"
+0x1000 0x000a "sym53c8xx" "Symbios|53c1510"
0x1000 0x0701 "yellowfin" "Symbios|83C885 gigabit ethernet"
0x1000 0x0702 "yellowfin" "Symbios|Yellowfin G-NIC gigabit ethernet"
0x1000 0x0901 "unknown" "Symbios|61C102"
Analyzing the above Example:
This example was created using the
following diff command: diff -u old/modules/pcitable new/modules/pcitable
However, now I would
probably only use the -Naur options instead of just -u. This example modifies
two files: new/modules/pcitable, and new/usr/share/kudzu/pcitable.
The
first patch header has two hunks. These particular hunks are adding 2 lines and
1 line respectively.
Search this Site!:
Homepage: http://www.cpqlinux.com/
Site Map: http://www.cpqlinux.com/sitemap.html