source: trunk/third/rcs/ @ 9047

Revision 9047, 55.4 KB checked in by ghudson, 28 years ago (diff)
This commit was generated by cvs2svn to compensate for changes in r9046, which included commits to RCS files with non-trunk default branches.
1.\" Format this file with:
2.\" pic file | tbl | troff -ms
4.\" \*s stands for $, and avoids problems when this file is checked in.
5.ds s $ D(
7.DS VS 12p
9.vs 12p
11.. D)
13.DE VS 18p
15.vs 18p
17.. Id
19.ND \\$4
21.Id $Id:,v 1996-10-04 05:52:39 ghudson Exp $
24RCS\*-A System for Version Control
27Walter F. Tichy
29Department of Computer Sciences
30Purdue University
31West Lafayette, Indiana 47907
34An important problem in program development and maintenance is version control,
35i.e., the task of keeping a software system consisting of many versions and
36configurations well organized.
37The Revision Control System (RCS)
38is a software tool that assists with that task.
39RCS manages revisions of text documents, in particular source programs,
40documentation, and test data.
41It automates the storing, retrieval, logging and identification of revisions,
42and it provides selection mechanisms for composing configurations.
43This paper introduces basic version control concepts and
44discusses the practice of version control
45using RCS.
46For conserving space, RCS stores deltas, i.e., differences between
47successive revisions.  Several delta storage methods are discussed.
48Usage statistics show that RCS's delta storage method is
49space and time efficient.
50The paper concludes with a detailed survey of version control tools.
52\fBKeywords\fR: configuration management, history management,
53version control, revisions, deltas.
56An earlier version of this paper was published in
57.I "Software\*-Practice & Experience"
58.B 15 ,
597 (July 1985), 637-654.
60.FE VS 18p
66Version control is the task of keeping software
67systems consisting of many versions and configurations well organized.
68The Revision Control System (RCS) is a set of UNIX
69commands that assist with that task.
71RCS' primary function is to manage \fIrevision groups\fR.
72A revision group is a set of text documents, called \fIrevisions\fR,
73that evolved from each other.  A new revision is
74created by manually editing an existing one.
75RCS organizes the revisions into an ancestral tree.  The initial revision
76is the root of the tree, and the tree edges indicate
77from which revision a given one evolved.
78Besides managing individual revision groups, RCS provides
79flexible selection functions for composing configurations.
80RCS may be combined with MAKE\u1\d,
81resulting in a powerful package for version control.
83RCS also offers facilities for
84merging updates with customer modifications,
85for distributed software development, and
86for automatic identification.
87Identification is the `stamping'
88of revisions and configurations with unique markers.
89These markers are akin to serial numbers,
90telling software maintainers unambiguously which configuration
91is before them.
93RCS is designed for both production and experimental
95In production environments,
96access controls detect update conflicts and prevent overlapping changes.
97In experimental environments, where strong controls are
98counterproductive, it is possible to loosen the controls.
100Although RCS was originally intended for programs, it is useful for any
101text that is revised frequently and whose previous revisions must be
102preserved.  RCS has been applied successfully to store the source
103text for drawings, VLSI layouts, documentation, specifications,
104test data, form letters and articles.
106This paper discusses the practice of
107version control using RCS.
108It also introduces basic version control concepts,
109useful for clarifying current practice and designing similar systems.
110Revision groups of individual components are treated in the next three sections,
111and the extensions to configurations follow.
112Because of its size, a survey of version control tools
113appears at the end of the paper.
115Getting started with RCS
117Suppose a text file \fIf.c\fR is to be placed under control of RCS.
118Invoking the check-in command
120ci  f.c
122creates a new revision group with the contents of
123\fIf.c\fR as the initial
124revision (numbered 1.1)
125and stores the group into the file \fIf.c,v\fR.
126Unless told otherwise, the command deletes \fIf.c\fR.
127It also asks for a description of the group.
128The description should state the common purpose of all revisions in the group,
129and becomes part of the group's documentation.
130All later check-in commands will ask for a log entry,
131which should summarize the changes made.
132(The first revision is assigned a default log message,
133which just records the fact that it is the initial revision.)
135Files ending in \fI,v\fR
136are called \fIRCS files\fR (\fIv\fR stands for \fIv\fRersions);
137the others are called working files.
138To get back the working file \fIf.c\fR in the previous example,
139execute the check-out command:
141co  f.c
144This command extracts the latest revision from
145the revision group \fIf.c,v\fR and writes
146it into \fIf.c\fR.
147The file \fIf.c\fR can now be edited and, when finished,
148checked back in with \fIci\fR:
150ci  f.c
152\fICi\fR assigns number 1.2 to
153the new revision.
154If \fIci\fR complains with the message
156ci error: no lock set by <login>
158then the system administrator has decided to configure RCS for a
159production environment by enabling the `strict locking feature'.
160If this feature is enabled, all RCS files are initialized
161such that check-in operations require a lock on the previous revision
162(the one from which the current one evolved).
163Locking prevents overlapping modifications if several people work on the same file.
164If locking is required, the revision should
165have been locked during the check-out by using
166the option \fI\-l\fR:
168co  \-l  f.c
170Of course it is too late now for the check-out with locking, because
171\fIf.c\fR has already been changed; checking out the file again
172would overwrite the modifications.
173(To prevent accidental overwrites, \fIco\fR senses the presence
174of a working file and asks whether the user really intended to overwrite it.
175The overwriting check-out is sometimes useful for
176backing up to the previous revision.)
177To be able to proceed with the check-in in the present case, first execute
179rcs  \-l  f.c
181This command retroactively locks the latest revision, unless someone
182else locked it in the meantime.  In this case, the two programmers
183involved have to negotiate whose
184modifications should take precedence.
186If an RCS file is private, i.e., if only the owner of the file is expected
187to deposit revisions into it, the strict locking feature is unnecessary and
188may be disabled.
189If strict locking is disabled,
190the owner of the RCS file need not have a lock for check-in.
191For safety reasons, all others
192still do.  Turning strict locking off and on is done with the commands:
194rcs  \-U  f.c       \fRand\fP         rcs  \-L  f.c
196These commands enable or disable the strict locking feature for each RCS file
198The system administrator only decides whether strict locking is
199enabled initially.
201To reduce the clutter in a working directory, all RCS files can be moved
202to a subdirectory with the name \fIRCS\fR.
203RCS commands look first into that directory for RCS files.
204All the commands presented above work
205with the \fIRCS\fR subdirectory without change.\(dg
206.FS \(dg
207Pairs of RCS and working files can actually be specified in 3 ways:
208a) both are given, b) only the working file is given, c) only the
209RCS file is given.
210If a pair is given, both files may have arbitrary path prefixes;
211RCS commands pair them up intelligently.
214It may be undesirable that \fIci\fR deletes the working file.
215For instance, sometimes one would like to save the current revision,
216but continue editing.
219ci  \-l  f.c
221checks in \fIf.c\fR as usual, but performs an additional
222check-out with locking afterwards.  Thus, the working file does
223not disappear after the check-in.
224Similarly, the option
225\fI\-u\fR does a check-in followed by a check-out without
226locking.  This option is useful if the file is needed for compilation after the check-in.
227Both options update the identification markers in the working file
228(see below).
230Besides the operations \fIci\fR and \fIco\fR, RCS provides the following
232.sp 0 VS 12p
234.vs 12p
237li l.
238ident%extract identification markers
239rcs%change RCS file attributes
240rcsclean%remove unchanged working files (optional)
241rcsdiff%compare revisions
242rcsfreeze%record a configuration (optional)
243rcsmerge%merge revisions
244rlog%read log messages and other information in RCS files
246A synopsis of these commands appears in the Appendix.
247.NH 2
248Automatic Identification
250RCS can stamp source and object code with special identification strings,
251similar to product and serial numbers.
252To obtain such identification, place the marker
256into the text of a revision, for instance inside a comment.
257The check-out operation will replace this marker with a string of the form
259\*sId:  filename  revisionnumber  date  time  author  state  locker \*s
261This string need never be touched, because \fIco\fR keeps it
262up to date automatically.
263To propagate the marker into object code, simply put
264it into a literal character string.  In C, this is done as follows:
266static char rcsid[] = \&"\*sId\*s\&";
268The command \fIident\fR extracts such markers from any file, in particular from
269object code.
270\fIIdent\fR helps to find out
271which revisions of which modules were used in a given program.
272It returns a complete and unambiguous component list,
273from which a copy of the program can be reconstructed.
274This facility is invaluable for program maintenance.
276There are several additional identification markers, one for each component
277of \*sId\*s.
278The marker
282has a similar function.  It accumulates
283the log messages that are requested during check-in.
284Thus, one can maintain the complete history of a revision directly inside it,
285by enclosing it in a comment.
286Figure 1 is an edited version of a log contained in revision 4.1 of
287the file \fIci.c\fR.  The log appears at the beginning of the file,
288and makes it easy to determine what the recent modifications were.
289.sp VS 12p
291.vs 12p 18 +0.5i
295/* +\w'/'u
297* \*sLog: ci.c,v \*s
298* Revision 4.1  1983/05/10 17:03:06  wft
299* Added option \-d and \-w, and updated assignment of date, etc. to new delta.
300* Added handling of default branches.
302* Revision 3.9  1983/02/15 15:25:44  wft
303* Added call to fastcopy() to copy remainder of RCS file.
305* Revision 3.8  1983/01/14 15:34:05  wft
306* Added ignoring of interrupts while new RCS file is renamed;
307* avoids deletion of RCS files by interrupts.
309* Revision 3.7  1982/12/10 16:09:20  wft
310* Corrected checking of return code from diff.
311* An RCS file now inherits its mode during the first ci from the working file,
312* except that write permission is removed.
313*/ 0
315.ce 1
316Figure 1.  Log entries produced by the marker \*sLog\*s. VS 18p
319.vs 18p
320.sp 0
322Since revisions are stored in the form of differences,
323each log message is
324physically stored once,
325independent of the number of revisions present.
326Thus, the \*sLog\*s marker incurs negligible space overhead.
328The RCS Revision Tree
330RCS arranges revisions in an ancestral tree.
331The \fIci\fR command builds this tree; the auxiliary command \fIrcs\fR
332prunes it.
333The tree has a root revision, normally numbered 1.1, and successive revisions
334are numbered 1.2, 1.3, etc.  The first field of a revision number
335is called the \fIrelease number\fR and the second one
336the \fIlevel number\fR.  Unless given explicitly,
337the \fIci\fR command assigns a new revision number
338by incrementing the level number of the previous revision.
339The release number must be incremented explicitly, using the
340\fI\-r\fR option of \fIci\fR.
341Assuming there are revisions 1.1, 1.2, and 1.3 in the RCS file f.c,v, the command
343ci  \-r2.1  f.c       \fRor\fP       ci  \-r2  f.c
345assigns the number 2.1 to the new revision.
346Later check-ins without the \fI\-r\fR option will assign the numbers 2.2, 2.3,
347and so on.
348The release number should be incremented only at major transition points
349in the development, for instance when a new release of a software product has
350been completed.
351.NH 2
352When are branches needed?
354A young revision tree is slender:
355It consists of only one branch, called the trunk.
356As the tree ages, side branches may form.
357Branches are needed in the following 4 situations.
358.IP "\fITemporary fixes\fR"
359.sp 0
360Suppose a tree has 5 revisions grouped in 2 releases,
361as illustrated in Figure 2.
362Revision 1.3, the last one of release 1, is in operation at customer sites,
363while release 2 is in active development. 4
365.PS 4i -2
367box "1.1"
369box "1.2"
371box "1.3"
373box "2.1"
375box "2.2"
376arrow dashed +2
379.ce 1
380Figure 2.  A slender revision tree.
381.sp 0
382Now imagine a customer requesting a fix of
383a problem in revision 1.3, although actual development has moved on
384to release 2.  RCS does not permit an extra
385revision to be spliced in between 1.3 and 2.1, since that would not reflect
386the actual development history.  Instead, create a branch
387at revision 1.3, and check in the fix on that branch.
388The first branch starting at 1.3 has number 1.3.1, and
389the revisions on that branch are numbered,, etc.
390The double numbering is needed to allow for another
391branch at 1.3, say 1.3.2.
392Revisions on the second branch would be numbered
3931.3.2.1,, and so on.
394The following steps create
395branch 1.3.1 and add revision
396.sp 0
397.I VS 12p
399.vs 12p
402l l l.
403     %co  \-r1.3  f.c% \*- check out revision 1.3
404     %edit  f.c% \*- change it
405     %ci  \-r1.3.1  f.c% \*- check it in on branch 1.3.1
406.TE VS 18p
408.vs 18p
410This sequence of commands transforms the tree of Figure 2 into
411the one in Figure 3.
412Note that it may be necessary to incorporate the differences
413between 1.3 and
414into a revision at level 2.  The operation \fIrcsmerge\fR automates this
415process (see the Appendix). 7
417.PS 4i -2
419     box "1.1"
420     arrow
421     box "1.2"
422     arrow
423R13: box "1.3"
424     arrow
425R21: box "2.1"
426     arrow
427R22: box "2.2"
428     arrow dashed
429     line invis down from R21.s
430RB1: box ""
431     arrow dashed right from RB1.e
432     arrow from R13.s to RB1.w +2
435.ce 1
436Figure 3.  A revision tree with one side branch
438.IP "\fIDistributed development and customer modifications\fR"
439.sp 0
440Assume a situation as in Figure 2, where revision 1.3 is in operation
441at several customer sites,
442while release 2 is in development.
443Customer sites should use RCS to store the distributed software.
444However, customer modifications should not be placed on the same branch
445as the distributed source; instead, they should be placed on a side branch.
446When the next software distribution arrives,
447it should be appended to the trunk of
448the customer's RCS file, and the customer
449can then merge the local modifications back into the new release.
450In the above example, a
451customer's RCS file would contain the following tree, assuming
452that the customer has received revision 1.3, added his local modifications
453as revision, then received revision 2.4, and merged
4542.4 and, resulting in 7
456.PS 4i -2
458R13: box "1.3"
459     line invis
460R21: box invis
461     line invis
462R22: box invis
463     line invis
464R24: box "2.4"
465     line invis
466R25: box invis
467     line invis
468     arrow from R13.e to R24.w
469     line invis down from R21.s
470RB1: box ""
471     arrow from R13.s to RB1.w
472     right
473     line invis down from R25.s
474RB2: box ""
475     arrow from R24.s to RB2.w +2
478.ce 1
479Figure 4.  A customer's revision tree with local modifications.
480.sp 1
481This approach is actually practiced in the CSNET project,
482where several universities and a company cooperate
483in developing a national computer network.
484.IP "\fIParallel development\fR"
485.sp 0
486Sometimes it is desirable to explore an alternate design or
487a different implementation technique in parallel with the
488main line development.  Such development
489should be carried out on a side branch.
490The experimental changes may later be moved into the main line, or abandoned.
491.IP "\fIConflicting updates\fR"
492.sp 0
493A common occurrence is that one programmer
494has checked out a revision, but cannot complete the assignment
495for some reason.  In the meantime, another person
496must perform another modification
497immediately.  In that case, the second person should check-out the same revision,
498modify it, and check it in on a side branch, for later merging.
500Every node in a revision tree consists of the following attributes:
501a revision number, a check-in date and time, the author's identification,
502a log entry, a state and the actual text.  All these attributes
503are determined at the time the revision is checked in.
504The state attribute indicates the status of a revision.
505It is set automatically to `experimental' during check-in.
506A revision can later be promoted to a higher status, for example
507`stable' or `released'.  The set of states is user-defined.
508.NH 2
509Revisions are represented as deltas
511For conserving space, RCS stores revisions in the form
512of deltas, i.e., as differences between revisions.
513The user interface completely hides this fact.
515A delta is a sequence of edit commands that transforms one string
516into another.  The deltas employed by RCS are line-based, which means
517that the only edit commands allowed are insertion and deletion of lines.
518If a single character in a line is changed, the
519edit scripts consider the entire line changed.
520The program \fIdiff\fR\u2\d
521produces a small, line-based delta between pairs of text files.
522A character-based edit script would take much longer to compute,
523and would not be significantly shorter.
525Using deltas is a classical space-time tradeoff: deltas reduce the
526space consumed, but increase access time.
527However, a version control tool should impose as little delay
528as possible on programmers.
529Excessive delays discourage the use of version controls,
530or induce programmers to take shortcuts that compromise system integrity.
531To gain reasonably fast access time for both editing and compiling,
532RCS arranges deltas in the following way.
533The most recent revision on the trunk is stored intact.
534All other revisions on the trunk are stored as reverse deltas.
535A reverse delta describes how to go backward in the development history:
536it produces the desired revision if applied to the successor of that revision.
537This implementation has the advantage
538that extraction of the latest revision is a simple and fast copy
540Adding a new revision to the trunk is also fast: \fIci\fR simply
541adds the new revision intact, replaces the previous
542revision with a reverse delta, and keeps the rest of the old deltas.
543Thus, \fIci\fR requires the computation
544of only one new delta.
546Branches need special treatment.  The naive solution would be to
547store complete copies for the tips of all branches.
548Clearly, this approach would cost too much space.  Instead,
549RCS uses \fIforward\fR deltas for branches.  Regenerating a revision
550on a side branch proceeds as follows.  First, extract the latest revision
551on the trunk; secondly, apply reverse deltas until the fork revision for
552the branch is obtained; thirdly, apply forward deltas until the desired
553branch revision is reached.  Figure 5 illustrates a tree with
554one side branch.  Triangles pointing to the left and right represent
555reverse and forward deltas, respectively. 8
557.PS 4i -2
559define BD X [line invis $1 right .5;
560line up .3 then left .5 down .3 then right .5 down .3 then up .3] X
562define FD X [line invis $1 right .5;
563line left .5 down .3 then up .6 then right .5 down .3;] X
566D11:    BD(" 1.1")
567        arrow right from D11.e
568D12:    BD(" 1.2")
569        arrow right from D12.e
570D13:    BD(" 1.3")
571        arrow right from D13.e
572D21:    BD(" 2.1")
573        arrow right from D21.e
574D22:    box "2.2"
575        line invis down from D21.s
576F1:     FD(" ")
577        arrow from to F1.w
578        arrow from F1.e right
579        right
580F2:     FD(" ") +2
583.ce 1
584Figure 5.  A revision tree with reverse and forward deltas.
585.sp 0
587Although implementing fast check-out for the latest trunk revision,
588this arrangement has the disadvantage that generation of other revisions
589takes time proportional to the number of deltas applied.  For example,
590regenerating the branch tip in Figure 5 requires application of five
591deltas (including the initial one).  Since usage statistics show that
592the latest trunk revision is the one that is retrieved in 95 per cent
593of all cases (see the section on usage statistics), biasing check-out time
594in favor of that revision results in significant savings.
595However, careful implementation of the delta application process is
596necessary to provide low retrieval overhead for other revisions, in
597particular for branch tips.
599There are several techniques for delta application.
600The naive one is to pass each delta to a general-purpose text editor.
601A prototype of RCS invoked the UNIX editor \fIed\fR both
602for applying deltas and for expanding the identification markers.
603Although easy to implement, performance was poor, owing to the
604high start-up costs and excess generality of \fIed\fR.  An intermediate
605version of RCS used a special-purpose, stream-oriented editor.
606This technique reduced the cost of applying a delta to the cost of
607checking out the latest trunk revision.  The reason for this behavior
608is that each delta application involves a complete pass over
609the preceding revision.
611However, there is a much better algorithm.  Note that the deltas are
612line oriented and that most of the work of a stream editor involves
613copying unchanged lines from one revision to the next.  A faster
614algorithm avoids unnecessary copying of character strings by using
615a \fIpiece table\fR.
616A piece table is a one-dimensional array, specifying how a given
617revision is `pieced together' from lines in the RCS file.
618Suppose piece table \fIPT\dr\u\fR represents revision \fIr\fR.
619Then \fIPT\dr\u[i]\fR contains the starting position of line \fIi\fR
620of revision \fIr\fR.
621Application of the next delta transforms piece table \fIPT\dr\u\fR
622into \fIPT\dr+1\u\fR.  For instance, a delete command removes a
623series of entries from the piece table.  An insertion command inserts
624new entries, moving the entries following the insertion point further down the
625array.  The inserted entries point to the text lines in the delta.
626Thus, no I/O is involved except for reading the delta itself.  When all
627deltas have been applied to the piece table, a sequential pass
628through the table looks up each line in the RCS file and copies it to
629the output file, updating identification markers at the same time.
630Of course, the RCS file must permit random access, since the copied
631lines are scattered throughout that file.  Figure 6 illustrates an
632RCS file with two revisions and the corresponding piece tables. 13
634.sp 6
635.ce 1
636\fIFigure 6 is not available.\fP
637.sp 5
638.ce 1
639Figure 6.  An RCS file and its piece tables
640.sp 0
642The piece table approach has the property that the time for applying a single
643delta is roughly determined by the size of the delta, and not by the
644size of the revision.  For example, if a delta is
64510 per cent of the size of a revision, then applying it takes only
64610 per cent of the time to generate the latest trunk revision.  (The stream
647editor would take 100 per cent.)
649There is an important alternative for representing deltas that affects
650performance.  SCCS\u3\d,
651a precursor of RCS, uses \fIinterleaved\fR deltas.
652A file containing interleaved deltas is partitioned into blocks of lines.
653Each block has a header that specifies to which revision(s) the block
654belongs.  The blocks are sorted out in such a way that a single
655pass over the file can pick up all the lines belonging to a given
656revision.  Thus, the regeneration time for all revisions is the same:
657all headers must be inspected, and the associated blocks either copied
658or skipped.  As the number of revisions increases, the cost of retrieving
659any revision is much higher than the cost of checking out the
660latest trunk revision with reverse deltas.  A detailed comparison
661of SCCS's interleaved deltas and RCS's reverse deltas can be found
662in Reference 4.
663This reference considers the version of RCS with the
664stream editor only.  The piece table method improves performance
665further, so that RCS is always faster than SCCS, except if 10
666or more deltas are applied.
668Additional speed-up for both delta methods can be obtained by caching
669the most recently generated revision, as has been implemented in DSEE.\u5\d
670With caching, access time to frequently used revisions can approach normal file
671access time, at the cost of some additional space.
673Locking: A Controversial Issue
675The locking mechanism for RCS was difficult to design.
676The problem and its solution are first presented in their `pure' form,
677followed by a discussion of the complications
678caused by `real-world' considerations.
680RCS must prevent two or more persons from depositing competing changes of the
681same revision.
682Suppose two programmers check out revision 2.4 and
683modify it.  Programmer A checks in a revision before programmer B\&.
684Unfortunately, programmer B has not seen A's
685changes, so the effect is that A's changes are covered up by B's deposit.
686A's changes are not lost since all revisions
687are saved, but they are confined to a single revision.\(dd
688.FS \(dd
689Note that this problem is entirely different from the atomicity problem.
690Atomicity means that
691concurrent update operations on the same RCS file cannot be permitted,
692because that may result in inconsistent data.
693Atomic updates are essential (and implemented in RCS),
694but do not solve the conflict discussed here.
697This conflict is prevented in RCS by locking.
698Whenever someone intends to edit a revision (as opposed
699to reading or compiling it), the revision should be checked out
700and locked,
701using the \fI\-l\fR option on \fIco\fR.  On subsequent check-in,
702\fIci\fR tests the lock and then removes it.
703At most one programmer at a time may
704lock a particular revision, and only this programmer may check in
705the succeeding revision.
706Thus, while a revision is locked, it is the exclusive responsibility
707of the locker.
709An important maxim for software tools like RCS is that they must
710not stand in the way of making progress with a project.
711This consideration leads to several weakenings of the locking mechanism.
712First of all, even if a revision is locked, it can
713still be checked out.  This is necessary if other people
714wish to compile or inspect the locked revision
715while the next one is in preparation.  The only operations they
716cannot do are to lock the revision or to check in the succeeding one.  Secondly,
717check-in operations on other branches in the RCS file are still possible; the
718locking of one revision does not affect any other revision.
719Thirdly, revisions are occasionally locked for a long period of time
720because a programmer is absent or otherwise unable to complete
721the assignment.  If another programmer has to make a pressing change,
722there are the following three alternatives for making progress:
723a) find out who is holding the lock and ask that person to release it;
724b) check out the locked revision, modify it, check it
725in on a branch, and merge the changes later;
726c) break the lock.  Breaking a lock leaves a highly visible
727trace, namely an electronic mail message that is sent automatically to the
728holder of the lock, recording the breaker and a commentary requested from him.
729Thus, breaking locks is tolerated under certain circumstances,
730but will not go unnoticed.
731Experience has shown that the automatic mail message attaches a high enough
732stigma to lock breaking,
733such that programmers break locks only in real emergencies,
734or when a co-worker resigns and leaves locked revisions behind.
736If an RCS file is private, i.e., when a programmer owns an RCS file
737and does not expect anyone else to perform check-in operations,
738locking is an unnecessary nuisance.
739In this case,
740the `strict locking feature' discussed earlier may be disabled,
741provided that file protection
742is set such that only the owner may write the RCS file.
743This has the effect that only the owner can check-in revisions,
744and that no lock is needed for doing so.
746As added protection,
747each RCS file contains an access list that specifies the users
748who may execute update operations.  If an access list is empty,
749only normal UNIX file protection applies.  Thus, the access list is
750useful for restricting the set of people who would otherwise have update
751permission.  Just as with locking, the access list
752has no effect on read-only operations such as \fIco\fR.  This approach
753is consistent with the UNIX philosophy of openness, which contributes
754to a productive software development environment.
756Configuration Management
758The preceding sections described how RCS deals with revisions of individual
759components; this section discusses how to handle configurations.
760A configuration is a set of revisions, where each revision comes
761from a different revision group, and the revisions are selected
762according to a certain criterion.
763For example,
764in order to build a functioning compiler, the `right'
765revisions from the scanner, the parser, the optimizer
766and the code generator must be combined.
767RCS, in conjunction with MAKE,
768provides a number of facilities to effect a smooth selection.
769.NH 2
770RCS Selection Functions
772.IP "\fIDefault selection\fR"
773.sp 0
774During development, the usual selection criterion is to choose
775the latest revision of all components.  The \fIco\fR command
776makes this selection by default.  For example, the command
778co  *,v
780retrieves the latest revision on the default branch of each RCS file
781in the current directory.
782The default branch is usually the trunk, but may be
783set to be a side branch.
784Side branches as defaults are needed in distributed software development,
785as discussed in the section on the RCS revision tree.
787.IP "\fIRelease based selection\fR"
788.sp 0
789Specifying a release or branch number selects the latest revision in
790that release or branch.
791For instance,
793co  \-r2  *,v
795retrieves the latest revision with release number 2 from each RCS file.
796This selection is convenient if a release has been completed and
797development has moved on to the next release.
799.IP "\fIState and author based selection\fR"
800.sp 0
801If the highest level number within a given release number
802is not the desired one,
803the state attribute can help.  For example,
805co  \-r2  \-sReleased  *,v
807retrieves the latest revision with release number 2 whose state attribute
808is `Released'.
809Of course, the state attribute has to be set appropriately, using the
810\fIci\fR or \fIrcs\fR commands.
811Another alternative is to select a revision by its author,
812using the \fI\-w\fR option.
814.IP "\fIDate based selection\fR"
815.sp 0
816Revisions may also be selected by date.
817Suppose a release of an entire system was
818completed and current on March 4, at 1:00 p.m. local time.  Then the command
820co  \-d'March 4, 1:00 pm LT'  *,v
822checks out all the components of that release, independent of the numbering.
823The \fI\-d\fR option specifies a `cutoff date', i.e.,
824the revision selected has a check-in date that
825is closest to, but not after the date given.
826.IP "\fIName based selection\fR"
827.sp 0
828The most powerful selection function is based on assigning symbolic
829names to revisions and branches.
830In large systems, a single release number or date is not sufficient
831to collect the appropriate revisions from all groups.
832For example, suppose one wishes to combine release 2
833of one subsystem and release 15 of another.
834Most likely, the creation dates of those releases differ also.
835Thus, a single revision number or date passed to the \fIco\fR command
836will not suffice to select the right revisions.
837Symbolic revision numbers solve this problem.
838Each RCS file may contain a set of symbolic names that are mapped
839to numeric revision numbers.  For example, assume
840the symbol \fIV3\fR is bound to release number 2 in file \fIs,v\fR, and to
841revision number 15.9 in \fIt,v\fR.
842Then the single command
844co  \-rV3  s,v  t,v
846retrieves the latest revision of release 2 from \fIs,v\fR,
847and revision 15.9 from \fIt,v\fR.
848In a large system with many modules, checking out all
849revisions with one command greatly simplifies configuration management.
851Judicious use of symbolic revision numbers helps with organizing
852large configurations.
853A special command, \fIrcsfreeze\fR,
854assigns a symbolic revision number to a selected revision
855in every RCS file.
856\fIRcsfreeze\fR effectively freezes a configuration.
857The assigned symbolic revision number selects all components
858of the configuration.
859If necessary, symbolic numbers
860may even be intermixed with numeric ones.  Thus, \fIV3.5\fR in the
861above example
862would select revision 2.5 in \fIs,v\fR and branch 15.9.5 in \fIt,v\fR.
864The options \fI\-r\fR, \fI\-s\fR, \fI\-w\fR and \fI\-d\fR
865may be combined.  If a branch is given, the latest revision
866on that branch satisfying all conditions is retrieved;
867otherwise, the default branch is used.
868.NH 2
869Combining MAKE and RCS
872is a program that processes configurations.
873It is driven by configuration specifications
874recorded in a special file, called a `Makefile'.
875MAKE avoids redundant processing steps
876by comparing creation dates of source and processed objects.
877For example, when instructed to compile all
878modules of a given system, it only recompiles
879those source modules that were changed
880since they were processed last.
882MAKE has been extended with an auto-checkout feature for RCS.*
883.FS *
884This auto-checkout extension is available only in some versions of MAKE,
885e.g. GNU MAKE.
887When a certain file to be processed is not present,
888MAKE attempts a check-out operation.
889If successful, MAKE performs the required processing, and then deletes
890the checked out file to conserve space.
891The selection parameters discussed above can be passed to MAKE
892either as parameters, or directly embedded in the Makefile.
893MAKE has also been extended to search the subdirectory named \fIRCS\fR
894for needed files, rather than just the current working directory.
895However, if a working file is present, MAKE totally ignores the corresponding
896RCS file and uses the working file.
897(In newer versions of MAKE distributed by AT&T and others,
898auto-checkout can be
899achieved with the rule DEFAULT, instead of a special extension of MAKE.
900However, a file checked out by the rule DEFAULT
901will not be deleted after processing. \fIRcsclean\fR can be
902used for that purpose.)
904With auto-checkout, RCS/MAKE can effect a selection rule
905especially tuned for multi-person software development and maintenance.
906In these situations,
907programmers should obtain configurations that consist of
908the revisions they have personally checked out plus the latest
909checked in revision of all other revision groups.
910This schema can be set up as follows.
912Each programmer chooses a working directory
913and places into it a symbolic link, named \fIRCS\fR,
914to the directory containing the relevant RCS files.
915The symbolic link makes sure that \fIco\fR and \fIci\fR
916operations need only specify the working files, and that
917the Makefile need not be changed.
918The programmer then checks out the needed files and modifies them.
919If MAKE is invoked,
920it composes configurations by selecting those
921revisions that are checked out, and the rest from the
922subdirectory \fIRCS\fR.
923The latter selection may be controlled by a symbolic
924revision number or any of the other selection criteria.
925If there are several programmers editing in separate working directories,
926they are insulated from each other's changes until checking in their
929Similarly, a maintainer can recreate an older configuration
930by starting to work in an empty working directory.
931During the initial MAKE invocation, all revisions are selected from RCS files.
932As the maintainer checks out files and modifies them,
933a new configuration is gradually built up.
934Every time MAKE is invoked, it substitutes the modified revisions
935into the configuration being manipulated.
937A final application of RCS is to use it for storing Makefiles.
938Revision groups of Makefiles represent
939multiple versions of configurations.
940Whenever a configuration is baselined or distributed,
941the best approach is to unambiguously fix
942the configuration with a symbolic revision number by calling
944to embed that symbol into the Makefile, and to
945check in the Makefile (using the same symbolic revision number).
946With this approach, old configurations
947can be regenerated easily and reliably.
949Usage Statistics
951The following usage statistics were collected on two DEC VAX-11/780
952computers of the Purdue Computer Science Department.  Both machines
953are mainly used for research purposes.  Thus, the data
954reflect an environment in which the majority of projects
955involve prototyping and advanced software development,
956but relatively little long-term maintenance.
958For the first experiment,
959the \fIci\fR and \fIco\fR operations were instrumented
960to log the number of backward and forward deltas applied.
961The data were collected during a 13 month period
962from Dec. 1982 to Dec. 1983.
963Table I summarizes the results.
964.sp 0 VS 12p
966.vs 12p
969c|c|c|c|c s|c s
970c|c|c|c|c s|c s
971l|n|n|n|n n|n n.
972Operation#Total#Total deltas#Mean deltas#Operations#Branch
973         #operations #applied#applied#with >1 delta#operations
975co     # 7867# 9320#1.18#509#(6%)#203#(3%)
976ci     # 3468# 2207#0.64# 85#(2%)# 75#(2%)
977ci & co#11335#11527#1.02#594#(5%)#278#(2%)
979.ce 1
980Table I.  Statistics for \fIco\fR and \fIci\fR operations. VS 18p
982.vs 18p
984The first two lines show statistics for check-out and check-in;
985the third line shows the combination.
986Recall that \fIci\fR performs an implicit check-out to obtain
987a revision for computing the delta.
988In all measures presented, the most recent revision (stored intact)
989counts as one delta.  The number of deltas applied represents
990the number of passes necessary, where the first `pass' is a copying step.
992Note that the check-out operation is executed more than
993twice as frequently as the check-in operation.
994The fourth column gives the mean number of deltas
995applied in all three cases.
996For \fIci\fR, the mean number of deltas applied is less
997than one.
998The reasons are that the initial check-in requires no delta at all, and that
999the only time \fIci\fR requires more than one delta is for branches.
1000Column 5 shows the actual number of operations that applied more than one
1002The last column indicates that branches were not used often.
1004The last three columns demonstrate that the most recent trunk revision
1005is by far the most frequently accessed.
1006For RCS, check-out of
1007this revision is a simple copy operation, which is the absolute minimum
1008given the copy-semantics of \fIco\fR.
1009Access to older revisions and branches
1010is more common in non-academic environments,
1011yet even if access to older deltas were an order
1012of magnitude more frequent,
1013the combined average number of deltas applied would still be below 1.2.
1014Since RCS is faster than SCCS until up to 10 delta applications,
1015reverse deltas are clearly the method of choice.
1017The second experiment, conducted in March of 1984,
1018involved surveying the existing RCS files
1019on our two machines.  The goal was to determine the mean number of
1020revisions per RCS file, as well as the space consumed by them.
1021Table II shows the results.  (Tables I and II were produced at different
1022times and are unrelated.)
1023.sp 0 VS 12p
1025.vs 12p
1028c | c | c | c | c | c | c
1029c | c | c | c | c | c | c
1030l | n | n | n | n | n | n.
1031          #Total RCS#Total#Mean#Mean size of#Mean size of#Overhead
1032          #files#revisions#revisions#RCS files#revisions
1034All files #8033#11133#1.39#6156#5585#1.10
1035Files with#1477# 4578#3.10#8074#6041#1.34
1036\(>= 2 deltas
1038.ce 1
1039Table II.  Statistics for RCS files. VS 18p
1041.vs 18p
1043The mean number of revisions per RCS file is 1.39.
1044Columns 5 and 6 show the mean sizes (in bytes) of an RCS file
1045and of the latest revision of each RCS file, respectively.
1046The `overhead' column contains the ratio of the mean sizes.
1047Assuming that all revisions in an RCS file are approximately the same size,
1048this ratio gives a measure of the space consumed by the extra revisions.
1050In our sample, over 80 per cent of the RCS files contained only a single revision.
1051The reason is that our
1052systems programmers routinely check in all source files
1053on the distribution tapes, even though they may never touch them again.
1054To get a better indication of how much space savings are possible
1055with deltas, all measures with those files
1056that contained 2 or more revisions were recomputed.  Only for those files
1057is RCS necessary.
1058As shown in the second line, the average number of revisions for those files is
10593.10, with an overhead of 1.34.  This means that the extra 2.10 deltas
1060require 34 per cent extra space, or
106116 per cent per extra revision.
1063measured the space consumed by SCCS, and
1064reported an average of 5 revisions per group
1065and an overhead of 1.37 (or about 9 per cent per extra revision).
1066In a later paper, Glasser\u6\d
1067observed an average of 7 revisions per group in a single, large project,
1068but provided no overhead figure.
1069In his paper on DSEE\u5\d,
1070Leblang reported that delta storage combined with blank compression
1071results in an overhead of a mere 1\-2 per cent per revision.
1072Since leading blanks accounted for about 20 per cent of the surveyed Pascal
1073programs, a revision group with 5\-10 members was smaller
1074than a single cleartext copy.
1076The above observations demonstrate clearly that the space needed
1077for extra revisions is small.  With delta storage, the luxury of
1078keeping multiple revisions online is certainly affordable.
1079In fact, introducing a system with delta storage may reduce
1080storage requirements, because programmers often save back-up copies
1081anyway.  Since back-up copies are stored much more efficiently with deltas,
1082introducing a system such as RCS may
1083actually free a considerable amount of space.
1085Survey of Version Control Tools
1087The need to keep back-up copies of software arose when
1088programs and data were no longer stored on paper media, but were entered
1089from terminals and stored on disk.
1090Back-up copies are desirable for reliability, and many modern editors
1091automatically save a back-up copy for every file touched.
1092This strategy
1093is valuable for short-term back-ups, but not suitable for long-term
1094version control, since an existing back-up copy is overwritten whenever the
1095corresponding file is edited.
1097Tape archives are suitable for long-term, offline storage.
1098If all changed files are dumped on a back-up tape once per day, old revisions
1099remain accessible.  However, tape archives are unsatisfactory
1100for version control in several ways.  First, backing up the file
1101system every 24 hours does not capture intermediate revisions.
1102Secondly, the old revisions are not online,
1103and accessing them is tedious and time-consuming.
1104In particular, it is impractical to
1105compare several old revisions of a group,
1106because that may require mounting and searching several tapes.
1107Tape archives are important fail-safe tools in the
1108event of catastrophic disk failures or accidental deletions,
1109but they are ill-suited for version control.
1110Conversely, version control tools do not obviate the
1111need for tape archives.
1113A natural technique for keeping several old revisions online is
1114to never delete a file.
1115Editing a file
1116simply creates a new file with the same
1117name, but with a different sequence number.
1118This technique, available as an option in DEC's VMS operating system,
1119turns out to be inadequate for version control.
1120First, it is prohibitively expensive in terms of storage costs,
1121especially since no data compression techniques are employed.
1122Secondly, indiscriminately storing every change produces too many
1123revisions, and programmers have difficulties distinguishing them.
1124The proliferation of revisions forces programmers to spend much time on
1125finding and deleting useless files.
1126Thirdly, most of the support functions like locking, logging,
1127revision selection,
1128and identification described in this paper are not available.
1130An alternative approach is to separate editing from revision control.
1131The user may repeatedly edit a given revision,
1132until freezing it with an explicit command.
1133Once a revision is frozen, it is stored permanently and can no longer be modified.
1134(In RCS, freezing a revisions is done with \fIci\fR.)
1135Editing a frozen revision implicitly creates a new one, which
1136can again be changed repeatedly until it is frozen itself.
1137This approach saves exactly those revisions that the user
1138considers important, and keeps the number of revisions manageable.
1139IBM's CLEAR/CASTER\u7\d,
1140AT&T's SCCS\u3\d,
1141CMU's SDC\u8\d
1142and DEC's CMS\u9\d,
1143are examples of version control systems using this approach.
1144CLEAR/CASTER maintains a data base of programs, specifications,
1145documentation and messages, using deltas.
1146Its goal is to provide control over the development process from a
1147management viewpoint.
1148SCCS stores multiple revisions of source text in an ancestral tree,
1149records a log entry for each revision,
1150provides access control, and has facilities
1151for uniquely identifying each revision.
1152An efficient delta technique
1153reduces the space consumed by each revision group.
1154SDC is much simpler than SCCS because it stores not more than
1155two revisions.  However, it maintains a complete log for all old
1156revisions, some of which may be on back-up tape.
1157CMS, like SCCS, manages tree-structured revision groups,
1158but offers no identification mechanism.
1160Tools for dealing with configurations are still in a state of flux.
1161SCCS, SDC and CMS can be combined with MAKE or MAKE-like programs.
1162Since flexible selection rules are missing from all these tools,
1163it is sometimes difficult
1164to specify precisely which revision of each group
1165should be passed to MAKE for building a desired configuration.
1166The Xerox Cedar system\u10\d
1167provides a `System Modeller' that can rebuild
1168a configuration from an arbitrary set of module revisions.
1169The revisions of a module are only distinguished by creation time,
1170and there is no tool for managing groups.
1171Since the selection rules are primitive,
1172the System Modeller appears to be somewhat tedious to use.
1173Apollo's DSEE\u5\d
1174is a sophisticated software engineering environment.
1175It manages revision groups in a way similar to SCCS and CMS.  Configurations
1176are built using `configuration threads'.
1177A configuration thread states which revision of each group
1178named in a configuration should be chosen.
1179A configuration thread may contain dynamic specifiers
1180(e.g., `choose the revisions I am currently working on,
1181and the most recent revisions otherwise'), which are bound
1182automatically at build time.
1183It also provides a notification mechanism for alerting
1184maintainers about the need to rebuild a system after a change.
1186RCS is based on a general model for describing
1187multi-version/multi-configuration systems\u11\d.
1188The model describes systems using AND/OR graphs, where AND nodes represent
1189configurations, and OR nodes represent version groups.
1190The model gives rise to a suit of selection rules for
1191composing configurations, almost all of which are implemented in RCS.
1192The revisions selected by RCS are passed to MAKE for configuration building.
1193Revision group management is modelled after SCCS.
1194RCS retains SCCS's best features,
1195but offers a significantly simpler user interface,
1196flexible selection rules, adequate integration with MAKE
1197and improved identification.
1198A detailed comparison of RCS and SCCS appears in Reference 4.
1200An important component of all revision control systems
1201is a program for computing deltas.
1202SCCS and RCS use the program \fIdiff\fR\u2\d,
1203which first computes the longest common substring of two
1204revisions, and then produces the delta from that substring.
1205The delta is simply an edit script consisting of deletion and
1206insertion commands that generate one revision from the other.
1208A delta based on a longest common substring is not necessarily minimal,
1209because it does not take advantage of crossing block moves.
1210Crossing block moves arise if two or more blocks of lines
1211(e.g., procedures)
1212appear in a different order in two revisions.
1213An edit script derived from a longest common substring
1214first deletes the shorter of the two blocks, and then reinserts it.
1216proposed an algorithm for detecting block moves, but
1217since the algorithm is based on heuristics,
1218there are conditions
1219under which the generated delta is far from minimal.
1220DSEE uses this algorithm combined with blank compression,
1221apparently with satisfactory overall results.
1222A new algorithm that is guaranteed to produce a minimal delta based on
1223block moves appears in Reference 13.
1224A future release of RCS will use this algorithm.
1227Many people have helped make RCS a success by contributed criticisms, suggestions,
1228corrections, and even whole new commands (including manual pages).
1229The list of people is too long to be
1230reproduced here, but my sincere thanks for their help and
1231goodwill goes to all of them.
1232.sp VS 12p
1234.vs 12p
1236Appendix: Synopsis of RCS Operations
1238.IP "\fIci\fP \fB\- check in revisions\fP"
1239.sp 0
1240\fICi\fR stores the contents of a working file into the
1241corresponding RCS file as a new revision.
1242If the RCS file doesn't exist, \fIci\fR creates it.
1243\fICi\fR removes the working file, unless one of the options
1244\fI\-u\fR or \fI\-l\fR is present.
1245For each check-in, \fIci\fR asks for a commentary
1246describing the changes relative to the previous revision.
1247.sp 1
1248\fICi\fR assigns the revision number given by the \fI\-r\fR option;
1249if that option is missing, it derives the number from the
1250lock held by the user; if there is no lock and locking is not strict,
1251\fIci\fR increments the number of the latest revision on the trunk.
1252A side branch can only be started by explicitly specifying its
1253number with the \fI\-r\fR option during check-in.
1254.sp 1
1255\fICi\fR also determines
1256whether the revision to be checked in is different from the
1257previous one, and asks whether to proceed if not.
1258This facility simplifies check-in operations for large systems,
1259because one need not remember which files were changed.
1260.sp 1
1261The option \fI\-k\fR searches the checked in file for identification
1262markers containing
1263the attributes
1264revision number, check-in date, author and state, and assigns these
1265to the new revision rather than computing them.  This option is
1266useful for software distribution: Recipients of distributed software
1267using RCS should check in updates with the \fI\-k\fR option.
1268This convention guarantees that revision numbers, check-in dates,
1269etc., are the same at all sites.
1270.IP "\fIco\fP \fB\- check out revisions\fP"
1271.sp 0
1272\fICo\fR retrieves revisions according to revision number,
1273date, author and state attributes.  It either places the revision
1274into the working file, or prints it on the standard output.
1275\fICo\fR always expands the identification markers.
1276.IP "\fIident\fP \fB\- extract identification markers\fP"
1277.sp 0
1278\fIIdent\fR extracts the identification markers expanded by \fIco\fR
1279from any file and prints them.
1280.IP "\fIrcs\fP \fB\- change RCS file attributes\fP"
1281.sp 0
1282\fIRcs\fR is an administrative operation that changes access lists,
1283locks, unlocks, breaks locks, toggles the strict-locking feature,
1284sets state attributes and symbolic revision numbers, changes the
1285description, and deletes revisions.  A revision can
1286only be deleted if it is not the fork of a side branch. 10
1289.IP "\fIrcsclean\fP \fB\- clean working directory\fP"
1290.sp 0
1291\fIRcsclean\fR removes working files that were checked out but never changed.*
1292.FS *
1293The \fIrcsclean\fP and \fIrcsfreeze\fP commands
1294are optional and are not always installed.
1296.IP "\fIrcsdiff\fP \fB\- compare revisions\fP"
1297.sp 0
1298\fIRcsdiff\fR compares two revisions and prints their
1299difference, using the UNIX tool \fIdiff\fR.
1300One of the revisions compared may be checked out.
1301This command is useful for finding out about changes.
1302.IP "\fIrcsfreeze\fP \fB\- freeze a configuration\fP"
1303.sp 0
1304\fIRcsfreeze\fR assigns the same symbolic revision number
1305to a given revision in all RCS files.
1306This command is useful for accurately recording a configuration.*
1307.IP "\fIrcsmerge\fP \fB\- merge revisions\fP"
1308.sp 0
1309\fIRcsmerge\fR merges two revisions, \fIrev1\fR and \fIrev2\fR,
1310with respect to a common ancestor.
1311A 3-way file comparison determines the segments of lines that
1312are (a) the same in all three revisions, or (b) the same in 2 revisions,
1313or (c) different in all three.  For all segments of type (b) where
1314\fIrev1\fR is the differing revision,
1315the segment in \fIrev1\fR replaces the corresponding segment of \fIrev2\fR.
1316Type (c) indicates an overlapping change, is flagged as an error, and requires user
1317intervention to select the correct alternative.
1318.IP "\fIrlog\fP \fB\- read log messages\fP"
1319.sp 0
1320\fIRlog\fR prints the log messages and other information in an RCS file.
1322.LP VS 12p
1324.vs 12p
1326.ds [F 1
1328.ds [K FELD02
1329.ds [K MakeArticle
1330.ds [A Feldman, Stuart I.
1331.ds [D March 1979
1332.ds [T Make\*-A Program for Maintaining Computer Programs
1333.ds [J Software\*-Practice & Experience
1334.ds [V 9
1335.ds [N 3
1336.ds [P 255-265 [P 1 [T 0 [A 1 [O 0
1341.][ 1 journal-article
1342.ds [F 2
1344.ds [K HUNT01
1345.ds [T An Algorithm for Differential File Comparison
1346.ds [A Hunt, James W. [A " and McIlroy, M. D.
1348.ds [I Computing Science Technical Report, Bell Laboratories
1349.ds [R 41
1350.ds [D June 1976 [T 0 [A 1 [O 0
1354.][ 4 tech-report
1355.ds [F 3
1357.ds [K SCCS
1358.ds [A Rochkind, Marc J.
1359.ds [D Dec. 1975
1360.ds [T The Source Code Control System
1361.ds [J IEEE Transactions on Software Engineering
1362.ds [V SE-1
1363.ds [N 4
1364.ds [P 364-370 [P 1 [T 0 [A 1 [O 0
1369.][ 1 journal-article
1370.ds [F 4
1372.ds [K TICH08
1373.ds [T Design, Implementation, and Evaluation of a Revision Control System
1374.ds [A Tichy, Walter F.
1375.ds [B Proceedings of the 6th International Conference on Software Engineering
1376.ds [I ACM, IEEE, IPS, NBS
1377.ds [D September 1982
1378.ds [P 58-67 [P 1 [T 0 [A 1 [O 0
1383.][ 3 article-in-book
1384.ds [F 5
1386.ds [K LEBL01
1387.ds [A Leblang, David B. [A " and Chase, Robert P.
1389.ds [T Computer-Aided Software Engineering in a Distributed Workstation Environment
1390.ds [O Proceedings of the ACM SIGSOFT/SIGPLAN Software Engineering Symposium [O " on Practical Software Development Environments.
1392.ds [J SIGPLAN Notices
1393.ds [V 19
1394.ds [N 5
1395.ds [D May 1984
1396.ds [P 104-112 [P 1 [T 0 [A 1 [O 0
1401.][ 1 journal-article
1402.ds [F 1
1403.ds [F 3
1404.ds [F 6
1406.ds [K SCCSEval
1407.ds [A Glasser, Alan L.
1408.ds [D Nov. 1978
1409.ds [T The Evolution of a Source Code Control System
1410.ds [J Software Engineering Notes
1411.ds [V 3
1412.ds [N 5
1413.ds [P 122-125 [P 1
1415.ds [O Proceedings of the Software Quality and Assurance Workshop. [T 0 [A 1 [O 1
1419.][ 1 journal-article
1420.ds [F 5
1421.ds [F 7
1423.ds [K IBMClearCaster
1424.ds [A Brown, H.B.
1425.ds [D 1970
1426.ds [T The Clear/Caster System
1427.ds [J Nato Conference on Software Engineering, Rome [T 0 [A 1 [O 0
1431.][ 1 journal-article
1432.ds [F 3
1433.ds [F 8
1435.ds [K HabermannSDC
1436.ds [A Habermann, A. Nico
1437.ds [D Jan. 1979
1438.ds [T A Software Development Control System
1439.ds [I Technical Report, Carnegie-Mellon University, Department of Computer Science [T 0 [A 0 [O 0
1443.][ 2 book
1444.ds [F 9
1446.ds [K CMS
1447.ds [A DEC
1448.ds [T Code Management System
1449.ds [I Digital Equipment Corporation
1450.ds [O Document No.\ EA-23134-82
1451.ds [D 1982 [T 0 [A 0 [O 0
1455.][ 2 book
1456.ds [F 10
1458.ds [K LAMP01
1459.ds [A Lampson, Butler W. [A " and Schmidt, Eric E.
1461.ds [T Practical Use of a Polymorphic Applicative Language
1462.ds [B Proceedings of the 10th Symposium on Principles of Programming Languages
1463.ds [I ACM
1464.ds [P 237-255 [P 1
1466.ds [D January 1983 [T 0 [A 1 [O 0
1470.][ 3 article-in-book
1471.ds [F 5
1472.ds [F 11
1474.ds [K TICH07
1475.ds [T A Data Model for Programming Support Environments and its Application
1476.ds [A Tichy, Walter F.
1477.ds [B Automated Tools for Information System Design and Development
1478.ds [E Hans-Jochen Schneider and Anthony I. Wasserman
1479.ds [C Amsterdam
1480.ds [I North-Holland Publishing Company
1481.ds [D 1982 [T 0 [A 1 [O 0
1485.][ 3 article-in-book
1486.ds [F 4
1487.ds [F 2
1488.ds [F 12
1490.ds [K HECK01
1491.ds [T A Technique for Isolating Differences Between Files
1492.ds [A Heckel, Paul
1493.ds [J Communications of the ACM
1494.ds [D April 1978
1495.ds [V 21
1496.ds [N 4
1497.ds [P 264-268 [P 1 [T 0 [A 0 [O 0
1502.][ 1 journal-article
1503.ds [F 13
1505.ds [K TICH11
1506.ds [T The String-to-String Correction Problem with Block Moves
1507.ds [A Tichy, Walter F.
1508.ds [D Nov. 1984
1509.ds [J ACM Transactions on Computer Systems
1510.ds [V 2
1511.ds [N 4
1512.ds [P 309-321 [P 1 [T 0 [A 1 [O 0
1517.][ 1 journal-article
Note: See TracBrowser for help on using the repository browser.