summaryrefslogtreecommitdiff
blob: d179b4e65448de835692fe9a073e521d652356e8 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
Added support for Mercurial (hg) source control.  Mercurial is an
open-source distributed source control system, conceptually similar to
Git, Bazaar (bzr), Darcs, and the commercial system BitKeeper 
(which tkdiff already supports).  

While Mercurial already comes with a tkdiff wrapper called "hgdiff",
this script does not support arbitrary revisions in the way that the
actual hg diff command does (e.g. "hg diff -r2 -r5 filename).  This
patch gives tkdiff support for all the revision numbers that "hg diff"
supports.

The code changes are small and mostly boilerplate, but I did add one
new procedure called "is-mercurial-repository".  This was added
because mercurial uses a single ".hg" directory at the top-level
directory of a repository rather than having a directory at each
different directory inside the repository.  The new procedure simply
traverses up the parent directories until it either finds a .hg
directory (indicating that we're in a Mercurial repository) or hits
the root directory (indicating that we're not).

Since the list of supported source control systems is getting large, I
alphabetized the list in the command-line help text and also modified
other parts of this help text to say things like "RCS, CVS, etc."
rather than exhaustively listing all the supported systems yet again.

More information on Mercurial can be found at
  http://www.selenic.com/mercurial/wiki/ and
  http://en.wikipedia.org/wiki/Mercurial_(software)

diff -r 92c7c897cdd3 -r d32253d0cd0f tkdiff
--- a/tkdiff	Sat Jan 05 00:42:06 2008 -0800
+++ b/tkdiff	Wed Jan 09 06:05:01 2008 -0800
@@ -743,6 +743,7 @@ proc get-file-rev {f index {r ""}} {
         set bkopt ""
         set pvcsopt ""
         set p4file "$f"
+        set hgopt ""
     } else {
         set rev "r$r"
         set acrev "\"$r\""
@@ -754,6 +755,7 @@ proc get-file-rev {f index {r ""}} {
         set bkopt "-r$r"
         set pvcsopt "-r$r"
         set p4file "$f#$r"
+        set hgopt "-r$r"
     }
 
     set finfo(pth,$index) [tmpfile $index]
@@ -907,6 +909,23 @@ proc get-file-rev {f index {r ""}} {
             puts "Couldn't deal with $f, exiting..."
             exit
         }
+    } elseif {[is-mercurial-repository $dirname]} {
+        # mercurial support
+        set cmd "hg"
+        if {$::tcl_platform(platform) == "windows"} {
+            append cmd ".exe"
+        }
+        if {"$r" == "" || "$rev" == "PARENT"} {
+            # in hg, the revision for cat defaults to the parent revision
+            # of the working directory
+            set finfo(lbl,$index) "$f (HG PARENT)"
+            debug-info "  Setting lbl $finfo(lbl,$index)"
+            die-unless "exec $cmd cat $f" $finfo(pth,$index)
+        } else {
+            set finfo(lbl,$index) "$f (HG $rev)"
+            debug-info "  Setting lbl $finfo(lbl,$index)"
+            die-unless "exec $cmd cat $hgopt $f" $finfo(pth,$index)
+        }
     } else {
         fatal-error "File '$f' is not part of a revision control system"
     }
@@ -916,6 +935,19 @@ proc get-file-rev {f index {r ""}} {
         set finfo(lbl,$index) $finfo(userlbl,$index)
         debug-info "  User label: $finfo(lbl,$index)"
     }
+}
+
+proc is-mercurial-repository {dirname} {
+    # check for a .hg directory in all parent directories
+    set dirname [file normalize $dirname]
+    set prevdir {}
+    while {$dirname != $prevdir} {
+        set hgfilename [file join $dirname .hg]
+        if {[file isdirectory $hgfilename]} { return true }
+        set prevdir $dirname
+        set dirname [file dirname $dirname]
+    }
+    return false
 }
 
 proc sccs-is-bk {} {
@@ -6105,8 +6137,8 @@ proc do-usage {mode} {
     Plain file with conflict markers:
      	tkdiff -conflict FILE
 
-    Source control (AccuRev, BitKeeper, CVS, Subversion, Perforce, PVCS,
-      RCS, SCCS, ClearCase)
+    Source control (AccuRev, BitKeeper, ClearCase, CVS, Mercurial, Perforce, 
+      PVCS, RCS, SCCS, and Subversion)
      	tkdiff FILE
 	tkdiff -rREV FILE
 	tkdiff -rREV1 -rREV2 FILE
@@ -6125,7 +6157,9 @@ proc do-usage {mode} {
       directory with the same name. It detects and supports PVCS by looking \
       for a vcs.cfg file. It detects and supports AccuRev, Perforce and \
       ClearCase by looking for the environment variables named ACCUREV_BIN, \
-      P4CLIENT, and CLEARCASE_ROOT respectively.
+      P4CLIENT, and CLEARCASE_ROOT respectively.  It detects and supports \
+      Mercurial by looking for a directory named ".hg" in the current \
+      directory or any of its ancestor directories.
 
 In the first form, tkdiff will present a dialog to allow you to choose the \
       files to diff interactively. At present this dialog only supports a \
@@ -6139,9 +6173,9 @@ In the second form, at least one of the 
 
 In the remaining forms, <cmp>REV</cmp> (or <cmp>REV1</cmp> and \
       <cmp>REV2</cmp>) must be a valid revision number for <cmp>FILE</cmp>. \
-      Where AccuRev, RCS, CVS, Subversion, SCCS, PVCS or Perforce is implied \
+      When a source control system (RCS, CVS, etc.) is detected (see above) \
       but no revision number is specified, <cmp>FILE</cmp> is compared with \
-      the the revision most recently checked in.
+      the revision most recently checked in.
 
 To merge a file with conflict markers generated by "<cmp>merge</cmp>", \
       "<cmp>cvs</cmp>", or "<cmp>vmrg</cmp>", use \
@@ -6149,13 +6183,10 @@ To merge a file with conflict markers ge
       files which you can merge as usual (see below).
 
 For "<cmp>tkdiff FILE</cmp>" The CVS version has priority, followed by the \
-      Subversion version, followed by the SCCS version -- i.e. if a CVS \
+      Subversion version, followed by the SCCS version, followed by RCS, \
+      PVCS, Perforce, AccuRev, ClearCase, and Mercurial -- i.e. if a CVS \
       directory is present, CVS; if not and a Subversion directory is \
-      present, Subversion; if not and an SCCS directory is present, SCCS is \
-      assumed; otherwise, if a CVS.CFG file is found, PVCS is assumed; \
-      otherwise RCS is assumed. If none of the above apply and the AccuRev \
-      environment variable ACCUREV_BIN is found, AccuRev is used. If P4CLIENT \
-      is found, Perforce is used. If CLEARCASE_ROOT is found, ClearCase is used.
+      present, Subversion; etc.
 
 If the merge output filename is not specified, tkdiff will present a dialog \
       to allow you to choose the name of the merge output file.