Previous section   Next section

3.11 Binary Files and Wrappers

The default CVS method of handling file conflicts works well for text files, because CVS can determine which lines have changed and add or remove them as appropriate. It doesn't work well on binary files, because such files are not usually built around lines of text separated by carriage returns.

Some files with textual content are not actually text files. Files such as those created by Microsoft Word or OpenOffice should be flagged as binary, because line-by-line merging and keyword expansion could damage the saved data.

CVS doesn't work for device files, symbolic links, or other files that cannot be modified and moved. Rather than trying to store these files in CVS, include the commands to create or connect them in your build scripts.

For binary files, CVS uses a different method of conflict resolution. The two methods CVS has available are MERGE and COPY. MERGE is the default CVS method. COPY instructs CVS to provide the user with both versions of the file if there is a conflict, so the user can blend the changes manually and recommit.

Binary files should be added to CVS using the -kb command option to cvs add. If the expansion mode is not set at the time the file is added, the -kb command option to cvs admin will set the mode retroactively. This informs CVS not to expand keywords, not to modify line endings, and to use the COPY method of conflict resolution. Example 3-23 shows the use of these command options.

Example 3-23. Setting keyword expansion for binary files
bash-2.05a$ cvs add -kb Requirements.doc 
cvs server: scheduling file `Requirements.doc' for addition
cvs server: use 'cvs commit' to add this file permanently
bash-2.05a$ cvs add AcceptanceTest.doc 
cvs server: scheduling file `AcceptanceTest.doc' for addition
cvs server: use 'cvs commit' to add this file permanently
bash-2.05a$ cvs commit
.
.
.
bash-2.05a$ cvs admin -kb AcceptanceTest.doc 
RCS file: /var/lib/cvs/wizzard/doc/design/AcceptanceTest.doc,v
done

The flag to cvs add works well on a file-by-file basis, but when you need to add or import a large set of files, setting each binary file's expansion mode manually is annoying. CVS wrappers allow you to control the merge methodology or keyword-substitution modes used on a file, based on the filename (usually specified by the file extension). When a file matches a wrapper, the merge method or substitution mode in the wrapper is used instead of the method otherwise used in the command.

Wrappers can be specified using the -W command option for update and import, in the .cvswrappers file in the user's home directory on the client machine, or in the cvswrappers file in the repository's CVSROOT subdirectory.

The CVSWRAPPERS environment variable is read, but code comments imply that its behavior may change. The code currently reads one wrapper from this environment variable. If you are using a version of CVS later than 1.11.2, check the documentation to see whether multiple wrappers are read.

To specify a wrapper in a .cvswrappers or cvswrappers file, use the following syntax:

wildcard option 'value' [option 'value'...]

Specify a wrapper using the -W command option as follows:

 -W "wildcard option 'value'"

In the files, use one wrapper per line.

When using wrappers on the command line, use the shell escape character to escape any symbols that your shell tries to expand.

These are the available wrapper options:

-m

Indicates the merge methodology to be used for files that match the pattern. The values for -m are COPY or MERGE, described earlier in this section.

-k

Indicates the keyword-expansion mode to be used for files that match the pattern. The values for -k are the keyword-substitution modes explained in Section 3.10 in this chapter, without the -k prefix. For example, the value that indicates the binary-file mode is b, not -kb.

Replace wildcard in the wrapper syntax with a regular expression for pattern matching. Chapter 11 provides a full explanation of CVS pattern matching. These are the most important of the special symbols:

*

Matches any string, including the empty string

?

Matches any single character

Example 3-24 shows a cvs update using a wrapper parameter. (Note that I use the shell escape character for the bash shell to escape the asterisk.)

Example 3-24. Using cvs update with wrappers
bash-2.05a$ cvs update -W"Ma\* -k 'v'"
cvs server: Updating .
U Makefile
cvs server: Updating doc
cvs server: Updating doc/design
cvs server: Updating doc/plan
cvs server: Updating lib
cvs server: Updating man
cvs server: Updating src
bash-2.05a$ less Makefile
#
# Makefile for the Wizzard project
# First created by J Vesperman, 1 September 2002
#
# Current revision 1.3
# On branch  
# Latest change by jenn on 2002/09/12 12:57:40

Upgrade to at least CVS 1.10 before using wrappers to signal binary files. In CVS 1.9 and earlier, the COPY option of a wrapper overwrites a file rather than providing two versions.


  Previous section   Next section
Top