add checking for invalid entries in tag files
authorBenoit Boissinot <benoit.boissinot@ens-lyon.org>
Wed, 22 Mar 2006 05:30:47 +0100
changeset 1986 719cf07b076d
parent 1985 c577689006fa
child 1988 18a3e6369600
child 1990 4b0535c678d6
add checking for invalid entries in tag files safely parse the differents tag files, output warning when parsing an invalid entry.
mercurial/localrepo.py
tests/test-tags
tests/test-tags.out
--- a/mercurial/localrepo.py
+++ b/mercurial/localrepo.py
@@ -78,33 +78,43 @@ class localrepository(object):
         '''return a mapping of tag to node'''
         if not self.tagscache:
             self.tagscache = {}
-            def addtag(self, k, n):
-                try:
-                    bin_n = bin(n)
-                except TypeError:
-                    bin_n = ''
-                self.tagscache[k.strip()] = bin_n
 
-            try:
-                # read each head of the tags file, ending with the tip
-                # and add each tag found to the map, with "newer" ones
-                # taking precedence
-                fl = self.file(".hgtags")
-                h = fl.heads()
-                h.reverse()
-                for r in h:
-                    for l in fl.read(r).splitlines():
-                        if l:
-                            n, k = l.split(" ", 1)
-                            addtag(self, k, n)
-            except KeyError:
-                pass
+            def parsetag(line, context):
+                if not line:
+                    return
+                s = l.split(" ", 1)
+                if len(s) != 2:
+                    self.ui.warn(_("%s: ignoring invalid tag\n") % context)
+                    return
+                node, key = s
+                try:
+                    bin_n = bin(node)
+                except TypeError:
+                    self.ui.warn(_("%s: ignoring invalid tag\n") % context)
+                    return
+                if bin_n not in self.changelog.nodemap:
+                    self.ui.warn(_("%s: ignoring invalid tag\n") % context)
+                    return
+                self.tagscache[key.strip()] = bin_n
+
+            # read each head of the tags file, ending with the tip
+            # and add each tag found to the map, with "newer" ones
+            # taking precedence
+            fl = self.file(".hgtags")
+            h = fl.heads()
+            h.reverse()
+            for r in h:
+                count = 0
+                for l in fl.read(r).splitlines():
+                    count += 1
+                    parsetag(l, ".hgtags:%d" % count)
 
             try:
                 f = self.opener("localtags")
+                count = 0
                 for l in f:
-                    n, k = l.split(" ", 1)
-                    addtag(self, k, n)
+                    count += 1
+                    parsetag(l, "localtags:%d" % count)
             except IOError:
                 pass
 
--- a/tests/test-tags
+++ b/tests/test-tags
@@ -31,3 +31,13 @@ hg co -m 1
 hg id
 hg status
 
+hg commit -m "merge" -d "1000000 0"
+# invalid tags
+echo "spam" >> .hgtags
+echo >> .hgtags
+echo "foo bar" >> .hgtags
+echo "$T invalid" | sed "s/..../a5a5/" >> .hg/localtags
+hg commit -m "tags" -d "1000000 0"
+hg tags
+hg tip
+
--- a/tests/test-tags.out
+++ b/tests/test-tags.out
@@ -12,3 +12,17 @@ M a
 8216907a933d tip
 8216907a933d+8a3ca90d111d+ tip
 M .hgtags
+.hgtags:2: ignoring invalid tag
+.hgtags:4: ignoring invalid tag
+localtags:1: ignoring invalid tag
+tip                                4:fd868a874787a7b5af31e1675666ce691c803035
+first                              0:0acdaf8983679e0aac16e811534eb49d7ee1f2b4
+changeset:   4:fd868a874787
+.hgtags:2: ignoring invalid tag
+.hgtags:4: ignoring invalid tag
+localtags:1: ignoring invalid tag
+tag:         tip
+user:        test
+date:        Mon Jan 12 13:46:40 1970 +0000
+summary:     tags
+