This chapter describes how to keep your program or documentation source files well organized by using a version control system. A version control system automates the storage, retrieval, logging, identification, and merging of document revisions. Version control is most useful for text that is revised frequently, such as programs, documentation, graphics, papers, and so on. The Digital UNIX operating system provides the following two version control systems with slightly different features:
This chapter introduces basic version control concepts, describes how to use the RCS and SCCS commands and utilities, and provides more advanced information about using each system. Examples in this chapter describe a hypothetical kit for a product called "Orpheus Authoring Tools." The example kit is considered to be one of several Orpheus products. Because this particular kit is a document builder, the kit name is abbreviated as DCB and the main project directory is dcb_tools.
Using the Revision Control System (RCS) or the Source Code Control System (SCCS) lets you keep your source files in a common library and maintain control over them. Both systems provide easy-to-use, command-line interfaces. Knowing the basic commands lets you check in the source file to be modified into a version control file that contains all of the revisions of that source file. When you want to check out a version control file for editing, the system retrieves the revision or revisions you specify from the library and creates a working file for you to use.
Using more advanced interface commands lets you do the following:
Depending on your development environment and unique revision control requirements, you can select either RCS or SCCS as your version control system. Your choice depends on the amount of security and versatility you require. Table 6-1 summarizes some of the more widely used features of each system. docroff: ignoring superfluous symbol sccs_rcs_features
Feature | Comments |
Stores and retrieves multiple revisions of text. | Both systems provide a simple way to store and retrieve all changes made to a file. In addition, RCS can retrieve revisions based on ranges of revision numbers, symbolic names, dates, authors, and states. |
Maintains a complete history of changes. | Both systems log changes automatically. Besides the text of each revision, both systems store the author, date and time of the checkin, and a log message summarizing the changes. |
Resolves access conflicts. | Both systems prevent two people from modifying a file without each other's knowledge. |
Maintains tree of revisions. | Both systems can maintain separate lines of development for each file. |
Merges revised files with conflict resolution. | Both systems provide a way to merge changes to a file from two separate lines of development. RCS also alerts the user if there are overlapping changes to the file versions. |
Allows for release and configuration control. (RCS only) | RCS can assign symbolic names to revisions so that configurations of modules can be described simply and directly. |
Automates identification of each revision. | Both systems use keywords to tag revisions of files with name, revision number, time, author, and so on. |
RCS and SCCS store files in a reserved directory, called a version control library. The contents of each source file are stored as a single version control file (called an RCS-file in RCS or an s-file in SCCS). A version control file contains the original file (called a g-file in SCCS) together with all the changes, or deltas, that have been applied to it. Each delta is described by text telling who made the change and why. The change information itself is stored in the form of marked lines of text. Every line that is deleted or changed is marked as deleted but is not actually removed. New lines can be either edited versions of old lines or completely new material inserted at the appropriate places and marked. Your version control system can reconstruct any version of the file by applying all the deletions and additions for versions up to the desired version and by ignoring all later versions.
In RCS, RCS-files are identified by the suffix ,v added to their names; for example, attr,v would be the RCS-file for the source file named attr.
In SCCS, s-files are identified by the prefix s. added to their names; for example, s.attr would be the s-file for the source file named attr. Figure 6-1 illustrates the contents of a typical version control file. RCS and SCCS files contain the same kinds of information, but their organization is different.
A version identification number is applied to a particular revision of the version control file. In SCCS, this number is called an SID. The identification number for SCCS can contain up to four elements; RCS provides for additional elements. The first two elements are the release number and the level number within that release, and the third and fourth represent the same items of information (called the branch and the sequence) for a branched version of the file. (See Section 6.3.) Release identification numbers begin at 1. Level identification numbers within a release begin at .1 and advance by .1, so that the first version of a file is 1.1, the second version is 1.2, and so on. Figure 6-4 (in Section 6.3) illustrates the numbering sequence for one file's deltas.
A version control library is a directory in which all the version control files for a given project are stored. When you retrieve a file from the library, both RCS and SCCS provide a locking mechanism that prevents two people from accessing the file at the same time. File locking is discussed in detail in the following sections.
Usually, but not always, the library is given the name RCS or SCCS, depending on the system you use. Figure 6-2 and Figure 6-3 illustrate how a project's directory tree might appear with the RCS or SCCS library placed below the project's main directory.
Figure 6-2 shows three RCS-files. When a file is checked out of the library for editing, RCS correlates all the deltas and delivers a copy of the specified version, as illustrated here with the attr file. RCS also edits the RCS-file to insert the name of the person checking out the file. This information is stored in the $Locker$ keyword. See Section 6.5.2 for more information about using keywords in RCS.
RCS differs from SCCS in that file locking is enforced at checkin time. A file can be checked out by more than one person, but only the first person to check it out (the one holding the lock) can check it back in to the library. Even if a revision is locked, it can still be checked out for reading, compiling, and so on. Locking ensures that only one developer at a time can check in the next update of the file. In other words, locking prevents a checkin by anybody but the locker (the first person to check out the file).
If your RCS-file is private and you will be the only person making
revisions to it, you can turn off the strict locking feature of RCS.
When a file is checked back in, RCS removes the user's name from the
$Locker$
keyword. If strict locking is turned off, the owner of the file does
not need to have a lock for checkin, but all others do. Use the
following commands to turn strict locking off and on:
%
rcs -U filename
and
%
rcs -L filename
For more detailed information on file locking, refer to Section 6.5.3, Section 6.5.5, and the co(1) reference page.
Figure 6-3 shows three s-files and one other file, named p.attr, in the SCCS library. When a file is checked out of the library for editing, SCCS correlates all the deltas and delivers a copy of the specified version, as illustrated here with the attr file. SCCS also creates a lock file, called a p-file. If another person tries to check out the same file for editing, SCCS reports that the file is being edited and refuses to give access to the second person. A p-file has the letter p added as a prefix to its name. When a file is checked back in to the library, SCCS removes the p-file.
Usually, file versions progress in a straight line, with only one current version. In this case, file identification numbers contain two elements and progress by steps of .1, so that the first version number applied to a file is 1.1 and the eighth, for example, is 1.8.
Projects running in parallel to develop new versions of the same basic program can use the same version control file. As the different versions are put into the library, a tree develops. For example, suppose two teams begin development on separate versions of a file or module, starting from the most recent revision.
As the two development streams continue, a complex tree of deltas can be created, as illustrated in Figure 6-4.
To get or edit a file from one of the branches, you must specify its branch number. Figure 6-4 shows a tree for a version control file that consists of a main trunk (contains revisions numbers 1.1, 1.2, 1.3, and so on) and branches. For the delta numbers shown, the first two elements reflect the version number from which it is branched, and the second two elements reflect the new element's version number.
As an example, suppose the two development teams are working with revision number 1.2 of a file. Both RCS and SCCS will allocate a number of 1.3 to the first team to access the file. For the second team, the version control system will create a delta numbered 1.2.1.1. Because this is the first delta along this 1.2 branch, the last two elements of this version number are shown as 1.1.
As the two versions are developed, they can themselves be branched from; for example, a programmer might branch a new file from revision number 1.2.1.3 after revision number 1.2.1.4 has been created.
For more information and specific examples on branching in RCS and SCCS, see Section 6.5.5 and Section 6.6.5.
Once you have selected the version control system you want to use for your development project, you should create a directory in which you will place the RCS or SCCS files. Depending on the size and complexity of your development project, you might want to involve your system administrator, who can help you determine ownership and protection settings for the directory and source files.
When setting up your directory, you might want to assign ownership of the directory to the rcs or sccs user ID and set its permissions to prevent users other than rcs or sccs from writing to it. This method provides good security in that only RCS or SCCS can directly manipulate the files in the library.
If you are going to use the sccs command, the library's directory should be named SCCS, as illustrated in Figure 6-3. If the library directory is not named SCCS, you must use the -d option with the sccs command to access files in the library. (See Table 6-8.) For RCS, the directory should be named RCS; otherwise, you must specify a complete path (absolute or relative) to the RCS-file.
The RCS system provides a set of UNIX commands that assist in the task of version control for your text files. It is designed for both production and development environments where flexibility and file access control are high priorities. In production environments, access controls can detect update conflicts and prevent overlapping changes. In fast-changing development environments, where such strong controls may not be appropriate, users can easily modify the controls to suit individual project needs.
The RCS system comprises a set of independent commands.
Table 6-2
lists the RCS commands provided with Digital UNIX. The sections
following the table provide more information on some of these commands.
Refer to the appropriate reference page for additional information on
the available command options.
Command | Option | Description |
ci | Checks in revisions. Stores the contents of a working file in the corresponding RCS-file as a new revision. | |
-u or -l | Using one of these options prevents a working file from being deleted at checkin time. | |
-r | Assigns a revision number to the file being checked in. | |
-k | Searches the checked-in file for identification markers, and assigns them to new revisions. | |
co | Checks out revisions. Retrieves revisions according to revision number, date, author, and state attributes. Always expands the identification markers (keywords). | |
-l | Locks the revision during file checkout to prevent overlapping modifications if several people work on the same file. | |
ident | Extracts the identification markers from a file and prints them. The identification markers (keywords) are always expanded by co. | |
rcs | Changes RCS-file attributes. Changes (as an administrative operation) access lists, modifies file locking attributes, sets state attributes and symbolic revision numbers, changes the description, and deletes revisions. A revision can only be deleted if it is not the fork of a side branch. | |
-L | Sets the strict file locking mode. This means that the owner of an RCS-file must lock the file at checkin. This default is determined by the system administrator. | |
-U | Sets the nonstrict file locking mode. This means that the owner of the file does not need to lock the file at checkin. This default is determined by the system administrator. | |
rcsclean | Cleans your working directory. Removes working files that were checked out but never changed. | |
rcsdiff | Compares two revisions and prints out their differences, using the diff command. One of the revisions compared can be checked out. This command is useful for finding out about changes. | |
rcsfreeze | Freezes a configuration. Assigns the same symbolic revision number to a given revision in all RCS-files. This command is useful for accurately recording a configuration. | |
rcsmerge | Merges two revisions, rev1 and rev2, with respect to a common ancestor. A three-way file comparison determines the parts of lines that are the same in all three revisions, the same in two revisions, or different in all three. Overlapping changes are flagged and reported to the user. | |
-p | Prints the result of the merged files to the standard output; otherwise, the resulting merged file overwrites the working file. | |
rcsstat | Prints RCS-file status. Prints information about RCS-files, for example, the current version of the file selected with the -r option. | |
rcstime | Prints checkin time. Prints the time a particular revision of a given RCS-file was checked in to the system. The revision is selected by number and name, checkin date and time, author, or state. | |
rlog | Reads log messages. Prints the log messages and other information in an RCS-file, for example: RCS-file name, working file name, head (the number of the latest revision on the trunk), default branch, access list, locks, symbolic names, number of revisions and descriptive text. | |
-h | Prints only the RCS-file name, working file name, head, default branch, access list, locks, symbolic names, and suffix. | |
-t | Prints the same information as does -h, plus the descriptive text. |
You can use the
ci
command to place new files in a library. The following example assumes
that you are in the library's parent directory and want to add the
attr
file to the library:
%
ci attr
RCS/attr,v <---- attr initial revision: 1.1 enter description, terminate with ^D or '.': >> Orpheus Authoring Tools attr command >>^D done
The ci command creates the RCS-file attr,v and stores attr in it as revision 1.1. The command prompts you for a description, which should be a synopsis of the contents of the file. All later checkin commands will prompt you for a log entry, which should summarize the changes you made.
You can enter a series of files in a single operation. For example:
%
ci attr docbld dcb.ch-intro
The RCS system provides a syntax for including keywords or ID markers in source files to provide file-identification information. An ID marker consists of a keyword enclosed within dollar signs ($). When you retrieve a file from the RCS library, RCS expands the keyword by replacing it with the appropriate information, such as the file name or revision number.
RCS lets you use keyword markers anywhere in your file as literal
strings or comments to identify a revision. For example, if you place
the marker
$Header$
into your text file, RCS (with the
co
command) will replace this keyword with the following information:
$Header: filename revision_number date time author state$
Table 6-3 lists the RCS keywords and their corresponding values.
Keyword | Description |
$Author$ | The login name of the user who checked in the revision. |
$Date$ | The date and time the revision was checked in. |
$Header$ | A standard header containing the full pathname of the RCS-file, the revision number, the date, the author, the state, and the locker (if locked). |
$Id$ | Same as $Header$ except that the RCS-file name is without a path. |
$Locker$ | The login name of the user who locked the revision (empty if unlocked). |
$Log$ | The log message supplied during checkin, preceded by a header containing the RCS-file name, the revision number, the author, and the date. Existing log messages are not replaced; instead, the new log message is inserted after $Log:...$. |
$RCSfile$ | The name of the RCS-file without path. |
$Revision$ | The revision number assigned to the revision. |
$Source$ | The full pathname of the RCS-file. |
$State$ | The state assigned to the revision with the -s option of rcs or ci. |
The
ident
command finds and extracts keywords from any file, even object files
and dumps. It searches the files you specify for all occurrences of
the pattern
$keyword:...$.
For example, suppose the C program
myfile.c
contains the following information:
char resid [] = "$Header: Header information$"
The command
ident
will print the following:
myfile.c : $Header: Header information$
For more detailed information on using keywords in RCS, refer to the co(1) reference page.
To retrieve a file revision from an RCS-file, check it out of the RCS library by using the co command. The co command retrieves a revision from the RCS-file and stores it in a corresponding working file.
Revisions of an RCS-file can be checked out locked or unlocked.
Locking a revision prevents overlapping updates. When you check out a
file for reasons other than editing (reading or processing, for
example), the revision need not be locked. (A revision checked out for
editing and later checkin must normally be locked.) For example:
%
cd /usr/projects/dcb_tools
%
co -u attr
RCS/attr,v ----> attr revision 1.6 (unlocked) done
This command creates a copy of the most recent version of the RCS-file
(with keyword information included) and places it in your current
directory
(/usr/projects/dcb_tools
in this example). The
-u
option prevents RCS from locking the file. To get a copy of any
earlier version, use the
-r
option. For example, to retrieve version 1.5 of a file that is now at
version 1.8, you would use a command like the following:
%
cd /usr/projects/dcb_tools
%
co -r1.5 attr
RCS/attr,v ----> attr revision 1.5 done
You can also retrieve a series of files with a single
co
command. For
example:
%
co attr unstamp
RCS/attr,v ----> attr revision 1.5 done
RCS/unstamp,v ----> unstamp revision 1.2 done
To replace one or more edited files, use the ci command. This command places the contents of each working file in the corresponding RCS-file. Usually, RCS checks whether the revision to be deposited in the library is different from the preceding one, and alerts the user.
Also, because the ci command deletes your working files during checkin, you may want to use either the -l option or the -u option to preserve your working files by performing an implicit checkout operation. This is desirable if you want to save the current revisions and continue editing.
Section 6.3 provides an overview of branching concepts in a version control system. The following discussion provides specific examples that illustrate how RCS handles branching of multiple files.
RCS arranges file revisions in a tree of deltas. Each file in a revision tree contains the following kinds of information: a revision number, a checkin time and date, the author's identification, a log entry, a state, and the actual text. All of these file attributes are determined at the time the revision is checked in to the library. The "state" attribute indicates the status of the revision, which is set to "experimental" during checkin, but which can be later changed to "stable" or "released."
The
ci
command creates a revision tree with a root revision that is usually
numbered 1.1. Unless you specify a revision number explicitly,
ci
assigns new revision numbers by incrementing the level number of the
previous revision (1.2, 1.3, 1.4, and so on).
To begin a new release, use the following command:
%
ci -r2.1 unstamp
or
%
ci -r2 unstamp
This action assigns the number 2.1 to the new revision. Checking in the file to the library without the -r option automatically assigns the numbers 2.2, 2.3, and so on, to the later revisions of the file.
Suppose two development teams begin development on separate releases of
the
unstamp
command, beginning from revision number 1.2. At this point, both teams
can check out the latest revision by using the
co
command with the
-l
option as follows:
%
co -l unstamp
After editing the file, the first team can check in the file by using
the
ci
command, and will be alerted by RCS that the new revision number is
1.3. For example:
%
ci unstamp
RCS/unstamp,v <---- unstamp new revision 1.3; previous revision 1.2 enter log message: (terminate with a ^D or single '.') >> Changed defaults check. >>^D done
However, if the second team tries to check in the file with the same
action, RCS will issue the following message:
RCS/unstamp,v <----- unstamp ci error: no lock set by user-name
At this point, the second team can create a branch by using the
ci
command as follows:
%
ci -r1.3.1 unstamp
This action results in a branch with revision number 1.3.1.1. To
continue development along this branch, the second team should use the
current branch revision number on all subsequent checkouts of the file.
For example:
%
co -r1.3.1.1 unstamp
Creating new branches in RCS is accomplished through the use of the ci command; to continue development along a particular branch, use the -r option with the co command.
The preceding discussion describes how RCS handles revisions of individual files; the system also lets you work with groups (or sets) of files that you specify. See Section 6.5.8 for more information on working with file configurations in RCS.
You can examine an RCS-file for differences between versions with the rcsdiff command.
The
rcsdiff
command runs
diff
to compare two revisions of each RCS-file given. For example, to find
the differences between the latest version of the
attr
file (1.8, being edited to become 1.9) and the immediately preceding
version (1.7), you would use the following command:
%
rcsdiff -r1.7 attr
===================================== RCS file: RCS/attr,v retrieving revision 1.7 diff -r1.7 attr 31d30 < # and is version linked to the docbld command
To check the differences between versions 1.3 and 1.4 of the
attr
file, you would use the following command:
%
rcsdiff -r1.3 -r1.4 attr
==================================== RCS file: RCS/attr,v retrieving revision 1.3 retrieving revision 1.4 diff -r1.3 -r1.4 5a6 < uts=-04 --- > uts=-05
Use the
rlog
command to examine the revision history of a file. For example, the
rlog
command provides you with the following detailed information:
%
rlog unstamp
RCS file: RCS/unstamp,v; Working file: unstamp head: 1.2 branch: locks: ; strict access list: symbolic names: comment leader: "# " total revisions: 2; selected revisions: 2 description: unstamp source file _________________________ revision 1.2 date: 92/06/09 15:51:16; author:gunther; state:Exp; lines added/del: Fixed copyright notice _________________________ revision 1.1 date: 92/06/09 15:49:16; author:gunther; state:Exp; Initial revision
Note the type and amount of information that is available to you using the rlog command. RCS prints the following information for each RCS-file:
This information is followed by entries for the selected revisions in reverse chronological order for each branch. If entered without specifying options, rlog prints complete information for the file you select. See the rlog(1) reference page for more information on using options to restrict the output of the rlog command.
A configuration in RCS refers to a group or set of file revisions, in which each revision comes from a different file revision group. File revisions can be selected (checked out) according to certain criteria. You can check out sets of files from an RCS library based on the following selection criteria:
You can choose the latest revision of all files by default. For
example, the following command retrieves the latest revision on the
default branch of each RCS-file in the library:
%
co *,v
You can also specify a release or branch number to select the latest
revision in that release or branch. For example, the following command
retrieves the latest revision with release number 2 from each
RCS-file:
%
co -r2 *,v
You can select files according to state attributes. For
example, suppose you want to retrieve the latest revision with release
number 2 whose state attribute is "Released." This can be
accomplished by issuing the following command:
%
co -r2 -sReleased *,v
You can also select a revision by author, by using the -w option.
You can also select revisions by date. Suppose a release of an entire
system was completed and current as of June 15, at 2:00 p.m. The
following command checks out all files of that release, with the
-d
option specifying the cutoff date as June 15:
%
co -d "June 15,2:00 pm" *,v
You can assign symbolic names to revisions and branches. In large systems and development efforts, a single release number or date may not be sufficient to collect all the appropriate revisions from all groups.
For example, suppose you need to combine release 2 of one subsystem with release 10 of another. Most likely, the creation dates of these revisions will be different, so passing a single revision number or date to the co command will not be appropriate in this case. Using symbolic revision names can help solve this problem; each RCS-file can contain a set of symbolic names that are mapped to the numeric revision numbers.
For instance, suppose you set the symbolic name IFT2 to release number
2 in the file
attr,v
and to revision number 10.2 in
unstamp,v.
In this case, a single
co
command retrieves the latest revision of release 2 from
attr,v
and revision 10.2 from
unstamp,v
as follows:
%
co -rIFT2 attr,v unstamp,v
You can use the rcsfreeze command to assign a symbolic revision name to a set of RCS-files that form a configuration. To assign a unique symbolic revision name to the most recent revision of each RCS-file of the main trunk, use the rcsfreeze command each time a new version is checked in. For more information on assigning symbolic names to RCS-files, refer to the rcsfreeze(1) reference page.
For large software development efforts, the ability to retrieve all revisions with one command makes configuration management an organized and efficient task.
The SCCS system is composed of several independent commands, each of which can be used independently. The sccs command is a unified interface that simplifies the usage of the most common SCCS commands and provides several additional functions by combining the operations of multiple commands. It does not support all of the functions of the individual commands.
Each form of the sccs command includes the keyword sccs and the name of one function, such as edit, followed by options and the names of the file or files to be manipulated. Table 6-4 lists the sccs commands. The sections following the table provide more information on some of these commands. In these discussions, command options are omitted except where required. Commands that are also individual low level commands are indicated in the table. The complete list of individual commands is summarized in Table 6-9; for detailed information on their use, along with descriptions of their options, refer to their individual reference pages.
Command | Low | Description |
Name | Level | |
admin | Yes | Creates an s-file or changes some characteristic of an existing s-file. |
check | No | Reports on files being edited and the names of the users editing them. Differs from info in that check returns a meaningful exit status and displays no report if no files are being edited. |
clean | No | Removes from your directory all files that can be regenerated from the named s-file. |
create | No | Creates an s-file without removing the g-file. |
deledit | No | Performs a delta operation followed by an edit operation on the same file. |
delget | No | Performs a delta operation followed by a get operation on the same file. |
delta | Yes | Checks an edited g-file back into the library, recording the changes made and their history. Removes the p-file. |
diffs | No | Compares a g-file that is checked out for editing with an earlier version reconstructed from the s-file. |
edit | No | Checks out an s-file for editing; regenerates the g-file and places it in your directory. Creates a p-file. |
fix | No | Removes the most recent delta and presents the g-file for reediting. Same as entering rmdel followed by edit. |
get | Yes | Regenerates a g-file, usually but not always for a purpose other than editing. (The sccs edit command, which duplicates the function of sccs get -e, is the usual way to regenerate a g-file for editing.) |
help | Yes | Given a command name or an SCCS message number, displays information about that item. (The individual command's form is sccshelp.) Each SCCS message has an identification code; for example, the "no ID keywords" message's code is cm7. The sccs help cm7 command displays a description of this error. The sccshelp delta command returns a syntax diagram for the delta command. |
info | No | Reports on files being edited and the names of the users editing them. |
No | Displays the revision histories of the named file or files, then displays the SCCS file, with ID information added to the beginning of each line. | |
prs | Yes | Displays the revision histories of the named file or files. |
prt | No | Same as prs. |
rmdel | Yes | Removes the most recent delta from the specified branch of a named s-file. |
sccsdiff | Yes | Compares two versions of the s-file. Requires explicit specification of the s-file name. |
tell | No | Reports on files being edited. Differs from info in that only file names are reported. |
unedit | No | Aborts editing of a g-file. Deletes the p-file, releasing the s-file so that other users can check it out. If the g-file is present in your working directory, sccs unedit removes it and performs a get command on the s-file; if no g-file is present, no get command is executed. (Equivalent to the unget command.) |
what | Yes | Searches a file for an SCCS ID pattern and displays the text that follows it. |
You can use the
sccs
create
command to place new files in a library. The following example assumes
that you are in the library's parent directory and want to add the
attr
file to the library:
%
sccs create attr
attr: 1.1 141 lines
Do not include the prefix s. in the file name you specify; SCCS applies it automatically.
You can enter a series of files in a single operation. For example:
%
sccs create attr docbld dcb.ch-intro
After creating the s-file in the library, the sccs create command adds a comma as a prefix to the name of the original file; for example, attr becomes ,attr. This action preserves the original g-file with its keywords (if any) unexpanded. Then SCCS fetches a copy of the file by using a get command; this fetched version is ready for distribution.
You can also insert files in the library with the sccs admin -i command, using the following syntax:
sccs admin -i [ path/ ] input-file [ path/ ] s-filename
For example:
%
sccs admin -iunstamp unstamp
The name path/input-file specifies the input file. Regardless of the name of this file, the s-file will be named s.s-filename. Do not include any white space between the -i option and path/input-file. Do not include the prefix s. in s-filename; SCCS applies it automatically. Using the admin -i command avoids the renaming of the original g-file and the fetching of a version with expanded keywords. See Section 6.6.8 for more information on using the admin command.
You can use the
admin
-i
option to enter several files with a short shell script; the
following command-line example is implemented in
csh:
%
foreach x (attr docbld dcb.ch-intro)
?
sccs admin -i$x $x
?
end
The SCCS system provides a syntax for including ID keywords in source files to provide file-identification information. An ID keyword consists of a single letter enclosed within percent signs (%). When you retrieve a file for any purpose other than editing, SCCS expands each ID keyword by replacing it with the appropriate information, such as the SID or the file name. Table 6-5 lists the SCCS ID keywords.
Keyword | Description |
%B% | The branch number of a retrieved g-file |
%C% | The current line number in the file, intended to identify messages output by a program |
%D% | The retrieval date of a g-file retrieved by a get command in the form yy/mm/dd |
%E% | The creation date of a delta, in the form yy/mm/dd |
%F% | The file name of the s-file |
%G% | The creation date of a delta, in the form mm/dd/yy |
%H% | The retrieval date of a g-file retrieved by a get command, in the form mm/dd/yy |
%I% | The highest SID applied to the file retrieved |
%L% | The level number of a retrieved g-file |
%M% | The current module (file) name; for example, prog.c |
%P% | The full pathname of the s-file |
%Q% | The value of the q flag in the s-file |
%R% | The release number of a retrieved g-file |
%S% | The sequence number of a retrieved g-file |
%T% | The retrieval time of a g-file retrieved by a get command, in the form hh:mm:ss |
%U% | The creation time of a delta, in the form hh:mm:ss |
%W% | A shorthand for %Z%%M% [Tab] %I% |
%Y% | A placeholder for the value of the t flag (set by the admin command); not meaningful to SCCS itself |
%Z% | A placeholder that expands to the string @(#) for the what command to find |
SCCS handles ID keywords anywhere in a file. The purpose of the SCCS
what
command is to find and display expanded ID keywords in a file.
The
what
command searches for lines containing the string
@(#),
which is generated by the
%Z%
keyword or the
%W%
shorthand keyword, and displays those lines. For example:
%
what /usr/bin/attr
/usr/bin/attr: attr 1.8 of 4/15/92
The line displayed in this example is part of a shell script
and was coded as follows:
# SCCSID: %Z%%M% %I% of %G%
If your file does not contain ID keywords, SCCS reports that fact when you put the file in the library and when you retrieve it. You can set the file's i flag to specify that this condition will be a fatal error. (See Section 6.6.8 for a description of file flags.) The purpose of the i flag is to prevent a delta command from merging a g-file with expanded keywords (or with no keywords) with the s-file.
There are two reasons to get files from an SCCS library: for any use except editing, such as distribution, or for editing.
You can edit a file as part of the straight-line progress of its version history, or you can create a branching tree. Section 6.6.5 describes how to create a tree wherein multiple parallel versions are stored together in the same s-file.
For any use except editing, you get SCCS files with the
sccs
get
command. For example:
%
cd /usr/projects/dcb_tools
%
sccs get attr
1.8 126 lines
This command creates a copy of the most recent version of the s-file
with SCCS keywords expanded (see
Table 6-5)
and places it in your current directory
(/usr/projects/dcb_tools
in this example). To get a copy of any earlier version, use the
-rSID
option. For example, to retrieve version 1.5 of a file that is now
at version 1.8, you would use a command like the following:
%
cd /usr/projects/dcb_tools
%
sccs get -r1.5 attr
1.5 128 lines
See Section 6.6.5 for information on managing more complex trees of SCCS files.
You can use the -p option to retrieve a file and write it to standard output instead of implicitly creating a g-file with the same name as the s-file. See the get(1) reference page for more information.
To edit a file, check it out of the library with the
sccs
edit
command. For example:
%
sccs edit attr
1.8 new delta 1.9 126 lines
This command creates a copy of the most recent version of the s-file
with SCCS keywords unexpanded (see
Table 6-5)
and places it in your directory for editing. The command also creates
a p-file identifying the person who checked out the file for editing.
You can check on the status of files with the
sccs
info
command. For example:
%
sccs info
unstamp: is being edited: 1.4 1.5 gunther 92/09/07 10:42:19
You can also use the get -e command to retrieve a file for editing.
You can retrieve a series of files with a single
get
or
edit
command. For
example:
%
sccs get attr unstamp
SCCS/s.attr: 1.8 126 lines
SCCS/s.unstamp: 1.2 55 lines
If you specify the name SCCS instead of one or more file names, SCCS retrieves every s-file in the library.
To create a new release of a file, you fetch it using the
-r
option to specify the new release number in the
sccs
edit
command. For example, the following command initiates Release 2 of the
docbld
file:
%
sccs edit -r2 SCCS
SCCS/s.docbld: 1.50 new delta 2.1 1042 lines
SCCS/s.dcb_defaults: 1.50 new delta 2.1 63 lines
SCCS/s.dcb_diag.sed: 1.50 new delta 2.1 188 lines
To replace a file in the library you have edited, use the
sccs
delta
command. SCCS prompts you for a comment. For example:
%
sccs delta attr
Comments? (^D to end)
Changed defaults check. Now looks only for "flc="
[Ctrl/D]
1.9 4 inserted 4 deleted 124 unchanged
If you specify the name SCCS instead of one or more file names, SCCS performs a delta on every s-file in the library. Coupled with a similar edit command, this function is useful for sets of files that must be kept in version synchronization even when not all of them are edited. SCCS asks for comments only once and applies the same comment to each file.
The sccs delget and sccs deledit commands perform a delta followed by a get or an edit operation respectively.
Section 6.3 provides an overview of branching concepts in a version control system. The following section provides specific examples that illustrate how SCCS handles branching of multiple versions of files.
Suppose two development teams begin development on separate versions of
the
unstamp
file, beginning from SID 1.2. To enable branching, run the
sccs
admin
-fb
command as follows:
%
sccs admin -fb unstamp
The first team uses an
edit
command to create version 1.3 as follows:
%
sccs edit unstamp
1.2 new delta 1.3 55 lines
The second team uses an
edit
-b
command to create a branch as follows:
%
sccs edit -b unstamp
1.2 new delta 1.2.1.1 55 lines
Consider now a tree for the
unstamp
file with a main trunk and branches numbered 1.2.1, 1.2.2, and 1.3.1.
To get the latest version from branch 1.2.2 for distribution, you would
use the following command:
%
sccs get -r1.2.2 unstamp
1.2.2.1 55 lines
As an SCCS tree becomes more complex, ensuring that you have the latest delta for editing can become cumbersome because you must know the delta you want to retrieve. You can use the -t option to the sccs get and sccs edit commands to specify the absolute latest delta regardless of its SID.
You can merge a branched SCCS file back into the main trunk
by using the
sccs
edit
-i
command and by specifying the version or versions you want to merge.
For example, the following command creates version 1.5 of the
unstamp
command, including all the deltas in the range from 1.2.1.1 to 1.2.1.3.
The deltas are correlated so that the result is the accumulation of all
specified changes.
%
sccs edit -i1.2.1.1-1.2.1.3 unstamp
Included: 1.2.1.1 1.2.1.2 1.2.1.3 1.4 new delta 1.5 55 lines
You can examine an SCCS file for differences between versions with either the sccs diffs command or the sccsdiff command, depending on what forms of the file are available.
The
sccs
diffs
command compares the g-file with the specified version of the s-file.
For example, to find the differences between the latest version of the
attr
file (1.8, being edited to become 1.9) and the immediately preceding
version (1.7) you would use the following command:
%
sccs diffs -r1.7 attr
------- attr ------- 31d30 < # and is version-linked to the docbld command
To check the differences between versions 1.3 and 1.4 of the
attr
file, you would use the following command:
%
sccs sccsdiff -r1.3 -r1.4 SCCS/s.attr
< uts=-04 --- > uts=-05
As this example shows, you can enter a pathname for the s-file itself. Because of this design, you can use this command from any directory instead of having to change to the directory containing the SCCS library.
Use the
sccs
prs
command to examine the revision history of a file. For example:
%
sccs prs unstamp
SCCS/s.unstamp:
D 1.2 92/09/20 11:23:36 gunther 2 1 00000/00006/00055 [1] MRs: [2] COMMENTS: Fixed copyright notice
D 1.1 92/09/19 09:39:11 gunther 1 0 00061/00000/00000 MRs: COMMENTS: date and time created 92/09/19 09:39:11 by gunther
The D, MRs, and COMMENTS keywords indicated by callouts in this display are part of the complete set of SCCS keywords. Use the sccs help command to display a list of the keywords and their meanings.
Use the sccs get -m command to retrieve a copy of the file with SID numbers added as a prefix to each line. A file retrieved in this way shows you what delta produced every line in the retrieved version. Keep in mind that a given delta can be overlaid by later deltas; you might need to use the -r option to find particular changes.
The sccs admin command performs several administrative functions. Each function is specified by an option to the admin command, as described in Table 6-6.
Note
Your system administrator can set permissions so that only the administrator can use the admin command.
Option | Description |
-auser s-file | Adds the specified user to the list of users allowed to make changes to the named s-file. The user name can be a group ID; all users in that group are added. |
-dflag s-file | Turns off (deletes) the named flag in the s-file. |
-euser s-file | Removes the specified user from the list of users allowed to make changes to the named s-file. The user name can be a group ID; all users in that group are removed. |
-fflag s-file | Turns on the named flag in the s-file. |
-h s-file | Checks the structure of the named s-file and compares a newly computed checksum with the checksum that is stored in the s-file. This option helps you detect both accidental damage and damage caused by modifying SCCS files directly with non-SCCS commands. |
-iinput-file s-file | Creates SCCS/s.s-file, using input-file as the initial contents. Differs from sccs create in that admin -i does not rename the g-file or fetch a copy of the s-file; the g-file is left untouched in your directory. |
-mMR-list s-file | Specifies a list of Modification Request (MR) numbers to be inserted into the SCCS file as the reason for creating the initial delta. |
-ns-file | Creates an empty s-file. |
-rSID s-file | Specifies the initial SID when creating an s-file. |
-tfile s-file | Adds the contents of file to the s-file, flagging it as added text. If file is omitted, any such added text is deleted. Useful for including documentation to ensure its distribution with the s-file. |
-y"comment" s-file | Inserts the comment text in the initial delta in a manner identical to the workings of the delta command. The default comment, if the -y option is not used, is a line giving the date and time of the file's creation and the name of the user who created it. |
-z s-file | Recomputes the s-file's checksum in case the file has been corrupted. |
Caution
Using the val and admin -z commands to repair damaged s-files is risky and should be left to your system administrator or to a designated SCCS librarian.
The flags for the admin -f and admin -d options are described in Table 6-7.
Flag | Description |
b | Allows branches to be made using the -b flag to the edit command. |
cSID | Specifies SID as the highest delta that a get -e command can use. |
dSID | Specifies the default SID to be used on a get or edit command. |
fSID | Specifies SID as the lowest delta that a get -e command can use. |
i | Causes the "no Id keywords" error message to be a fatal error rather than a warning. |
j | Permits editing of the s-file by more than one person concurrently. |
lSID[,SID..] | Locks the specified SIDs from being retrieved for editing. You can lock all deltas with the -fla flag, and you can unlock specific deltas with the -d flag. |
mname | Substitutes name for all occurrences of the %M% keyword when keywords are expanded by a get command. The default name is the s-file's name without the s prefix. |
n | Causes the delta command to create a null delta in any releases that are skipped when a delta is made in a new release. For example, if you make delta 5.1 after delta 2.7, releases 3 and 4 will be null. The resulting null deltas can serve as points from which to build branch deltas. Without this flag, skipped releases do not appear in the s-file. |
q"text" | Substitutes text for all occurrences of the %Q% keyword when keywords are expanded by a get command. |
ttype | Substitutes type for all occurrences of the %Y% keyword when keywords are expanded by a get command. |
v[program] | Makes delta prompt for Modification Request (MR) numbers as the reason for creating a delta. The name program specifies the name of an MR number validity-checking program. (See the delta(1) reference page.) |
For example, the following command uses the contents of an existing
text file to create an s-file beginning at SID 2.1 and identified with
a comment. The s-file's
i
flag is set. The command places the resulting s-file in the SCCS
library under the user's working directory.
%
sccs admin -iunstamp -fi -r2 -y"Initial release" unstamp
This example does not destroy the original file.
The
sccs
command supports the options listed in
Table 6-8.
These options must include the SCCS function command keyword
as shown in the examples in the table. Do not include any space
between the options and their arguments.
Option | Description |
-ddirname |
Specifies a directory to use as the SCCS library's parent. Allows
access to SCCS libraries without requiring that your working directory
be the parent. For example:
%
pwd
1.8 126 lines
|
-ppath | Adds path to the final element of the pathname for the file you specify. By default, SCCS adds SCCS so that the path specified in the -d example resolves to /usr/src/dcb_tools/SCCS/s.attr. If your SCCS library is not named SCCS, use the -d option to modify this component of the path. |
-r | Runs with the real user's UID instead of changing to the sccs UID. For security purposes, SCCS normally sets the ownership of files in an SCCS library so that they belong to the sccs UID. This option is useful if you are using SCCS to manage a library for yourself only; you can create the SCCS directory with normal permissions, and the -r option will cause SCCS to manipulate files therein using your own UID. |
Table 6-9
provides a brief description of the individual SCCS commands.
Some of these commands are not
supported by the
sccs
command. Refer to the appropriate command's reference page
for more detailed information.
Supported | ||
Command | by sccs | Description |
Command | ||
admin | Yes | Creates an s-file or changes some characteristic of an existing s-file. |
cdc | No | Changes the comments associated with a delta. |
comb | No | Combines two or more consecutive deltas of an s-file into a single delta. Combining deltas can reduce storage requirements. |
delta | Yes | Checks an edited g-file back into the library, recording the changes made and their history. Removes the p-file. |
get | Yes | Gets a specified version of an s-file. Use this command to get a copy of a file to edit or compile. For editing, use the get -e command, which checks out an s-file for editing, regenerates the g-file and places it in your directory, and creates a p-file. |
prs | Yes | Displays the revision histories of the named s-file or s-files. |
rmdel | Yes | Removes the most recent delta from the specified branch of a named s-file. |
sccsdiff | Yes | Compares two versions of the s-file. Requires explicit specification of the s-file name. |
sccshelp | No | Provides an explanation of a diagnostic message or of an SCCS command name. |
unget | No | Removes the effect of a previous use of the get -e command by deleting the p-file and replacing the g-file with a copy having its ID keywords expanded. (Equivalent to the sccs unedit command.) |
val | No | Computes a checksum on an s-file to see if the result matches the checksum stored in the file. Use this command with the sccs admin -z command to detect and repair corrupted files. |
what | Yes | Searches a file for an SCCS ID pattern and displays the text that follows it. Use this command to find identifying information describing the source versions (kept under SCCS control) used to construct a program. |
Caution
Using the val and admin -z commands to repair damaged s-files is risky and should be left to your system administrator or to a designated SCCS librarian.
Table 6-10 provides a brief comparison of the operations of RCS and SCCS and the commands that are used to achieve similar functions. Refer to the reference pages for detailed information on using the individual commands.
Tasks | RCS Command | SCCS Commands |
Create a new file from your original. | ci file |
sccs create file sccs admin -isfile gfile admin -ipath/sfile gfile |
Get a copy of a file with expanded keywords. | co -u file |
sccs get file get file |
Get a copy of a file with unexpanded keywords. |
sccs get -k file get -k file |
|
Check out a file. | co -l file |
sccs edit file get -e file |
Check in an edited file. | ci file |
sccs delta file delta file |
Show revision histories
of a file. |
rlog file |
sccs prs file prs file |
Examine differences between file revisions. | rcsdiff -rrev file |
sccs diffs -rrev file sccsdiff -rrev -rrev file |
Merge file revisions. | rcsmerge -rrevs file | sccs edit -irevs file |
Find identifying information. | ident |
sccs
what
what |
Perform administrative tasks. | rcs | admin |
Clean up your directory.
(Remove unchanged files.) |
rcsclean | sccs clean |