Merge with TAH
-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1
Merge with TAH
fixup history messages to not interfere with GPG signing
manifest hash:
aea3a92e4699dfe0cbd98e6e2c8c6971218a59b8
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.0 (GNU/Linux)
iD8DBQFCrkK4ywK+sNU5EO8RAqxHAKCNyjTE5F/7EvM+ipjhgzIUk1aWZACgm7zz
eBcKlHcOA8ceUcn4IEBLQpM=
=YfHT
-----END PGP SIGNATURE-----
--- a/README Mon Jun 13 08:49:21 2005 +0100
+++ b/README Mon Jun 13 18:36:40 2005 -0800
@@ -59,7 +59,7 @@
$ cd ..
$ mkdir linux-work
$ cd linux-work
- $ hg branch ../linux # create a new branch
+ $ hg init ../linux # create a new branch
$ hg update # populate the working directory
$ <make changes>
$ hg commit
@@ -100,6 +100,9 @@
# export your current repo via HTTP with browsable interface
foo$ hg serve -n "My repo" -p 80
+ # pushing changes to a remote repo with SSH
+ foo$ hg push ssh://user@example.com/~/hg/
+
# merge changes from a remote machine
bar$ hg pull http://foo/
bar$ hg co # merge changes into your working directory
@@ -110,10 +113,10 @@
Symbolic repository names:
- Mercurial uses an optional file called ~/.hgpaths to track repo
- locations symbolically. Simply add a line with the name, a space, and
- a URL:
+ Mercurial uses an options file called ~/.hgrc. To track locations
+ symbolically, add a section to it like this:
- foo$ echo "main http://selenic.com/hg/" >> ~/.hgpaths
- foo$ hg merge main
- foo$ hg co
+ [paths]
+ main = http://selenic.com/hg
+ hgweb = http://edge2.net/hg/hgweb/
+ hgdoc = http://edge2.net/hg/man/
--- a/doc/hg.1.txt Mon Jun 13 08:49:21 2005 +0100
+++ b/doc/hg.1.txt Mon Jun 13 18:36:40 2005 -0800
@@ -188,6 +188,22 @@
(which could be a local path or a remote URI), the format is
<symbolic name> <repository path> with each mapping on a seperate line
+NON_TRANSPARENT PROXY SUPPORT
+-----
+
+ To access a mercurial repository through a proxy,
+ create a file $HOME/.hgrc in the following format:
+
+[http_proxy]
+host=myproxy:8080
+user=<username>
+passwd=<password>
+no=<localhost1>,<localhost2>,<localhost3>,...
+
+ "user","passwd" fields are used for authenticating proxies,
+ "no" is a comma-separated list of local host names
+ for which proxy must be bypassed.
+
BUGS
----
Probably lots, please post them to the mailing list (See Resources below)
--- a/mercurial/commands.py Mon Jun 13 08:49:21 2005 +0100
+++ b/mercurial/commands.py Mon Jun 13 18:36:40 2005 -0800
@@ -118,8 +118,12 @@
time.localtime(float(changes[2].split(' ')[0]))))
ui.note("files: %s\n" % " ".join(changes[3]))
if description:
- ui.status("description: %s\n" % description[0])
- ui.note(''.join(["| %s\n" % line.rstrip() for line in description[1:]]))
+ if ui.verbose:
+ ui.status("description:\n")
+ ui.status(changes[4].strip())
+ ui.status("\n")
+ else:
+ ui.status("summary: %s\n" % description[0])
ui.status("\n")
def help(ui, cmd=None):
--- a/mercurial/hg.py Mon Jun 13 08:49:21 2005 +0100
+++ b/mercurial/hg.py Mon Jun 13 18:36:40 2005 -0800
@@ -723,38 +723,50 @@
if not unknown:
self.ui.status("nothing to do!\n")
return None
-
+
+ rep = {}
+ reqcnt = 0
+
unknown = remote.branches(unknown)
while unknown:
- n = unknown.pop(0)
- seen[n[0]] = 1
-
- self.ui.debug("examining %s:%s\n" % (short(n[0]), short(n[1])))
- if n == nullid: break
- if n in seenbranch:
- self.ui.debug("branch already found\n")
- continue
- if n[1] and n[1] in m: # do we know the base?
- self.ui.debug("found incomplete branch %s:%s\n"
- % (short(n[0]), short(n[1])))
- search.append(n) # schedule branch range for scanning
- seenbranch[n] = 1
- else:
- if n[2] in m and n[3] in m:
- if n[1] not in fetch:
- self.ui.debug("found new changeset %s\n" %
- short(n[1]))
- fetch.append(n[1]) # earliest unknown
- continue
+ r = []
+ while unknown:
+ n = unknown.pop(0)
+ if n[0] in seen:
+ continue
- r = []
- for a in n[2:4]:
- if a not in seen: r.append(a)
-
- if r:
- self.ui.debug("requesting %s\n" %
- " ".join(map(short, r)))
- for b in remote.branches(r):
+ self.ui.debug("examining %s:%s\n" % (short(n[0]), short(n[1])))
+ if n[0] == nullid:
+ break
+ if n in seenbranch:
+ self.ui.debug("branch already found\n")
+ continue
+ if n[1] and n[1] in m: # do we know the base?
+ self.ui.debug("found incomplete branch %s:%s\n"
+ % (short(n[0]), short(n[1])))
+ search.append(n) # schedule branch range for scanning
+ seenbranch[n] = 1
+ else:
+ if n[1] not in seen and n[1] not in fetch:
+ if n[2] in m and n[3] in m:
+ self.ui.debug("found new changeset %s\n" %
+ short(n[1]))
+ fetch.append(n[1]) # earliest unknown
+ continue
+
+ for a in n[2:4]:
+ if a not in rep:
+ r.append(a)
+ rep[a] = 1
+
+ seen[n[0]] = 1
+
+ if r:
+ reqcnt += 1
+ self.ui.debug("request %d: %s\n" %
+ (reqcnt, " ".join(map(short, r))))
+ for p in range(0, len(r), 10):
+ for b in remote.branches(r[p:p+10]):
self.ui.debug("received %s:%s\n" %
(short(b[0]), short(b[1])))
if b[0] not in m and b[0] not in seen:
@@ -762,10 +774,13 @@
while search:
n = search.pop(0)
+ reqcnt += 1
l = remote.between([(n[0], n[1])])[0]
+ l.append(n[1])
p = n[0]
f = 1
- for i in l + [n[1]]:
+ for i in l:
+ self.ui.debug("narrowing %d:%d %s\n" % (f, len(l), short(i)))
if i in m:
if f <= 2:
self.ui.debug("found new branch changeset %s\n" %
@@ -785,6 +800,8 @@
self.ui.note("adding new changesets starting at " +
" ".join([short(f) for f in fetch]) + "\n")
+ self.ui.debug("%d total queries\n" % reqcnt)
+
return remote.changegroup(fetch)
def changegroup(self, basenodes):
@@ -1228,6 +1245,36 @@
def __init__(self, ui, path):
self.url = path
self.ui = ui
+ no_list = [ "localhost", "127.0.0.1" ]
+ host = ui.config("http_proxy", "host")
+ user = ui.config("http_proxy", "user")
+ passwd = ui.config("http_proxy", "passwd")
+ no = ui.config("http_proxy", "no")
+ if no:
+ no_list = no_list + no.split(",")
+
+ no_proxy = 0
+ for h in no_list:
+ if (path.startswith("http://" + h + "/") or
+ path.startswith("http://" + h + ":") or
+ path == "http://" + h):
+ no_proxy = 1
+
+ # Note: urllib2 takes proxy values from the environment and those will
+ # take precedence
+
+ proxy_handler = urllib2.BaseHandler()
+ if host and not no_proxy:
+ proxy_handler = urllib2.ProxyHandler({"http" : "http://" + host})
+
+ authinfo = None
+ if user and passwd:
+ passmgr = urllib2.HTTPPasswordMgrWithDefaultRealm()
+ passmgr.add_password(None, host, user, passwd)
+ authinfo = urllib2.ProxyBasicAuthHandler(passmgr)
+
+ opener = urllib2.build_opener(proxy_handler, authinfo)
+ urllib2.install_opener(opener)
def do_cmd(self, cmd, **args):
self.ui.debug("sending %s command\n" % cmd)
@@ -1235,7 +1282,7 @@
q.update(args)
qs = urllib.urlencode(q)
cu = "%s?%s" % (self.url, qs)
- return urllib.urlopen(cu)
+ return urllib2.urlopen(cu)
def heads(self):
d = self.do_cmd("heads").read()
--- a/mercurial/hgweb.py Mon Jun 13 08:49:21 2005 +0100
+++ b/mercurial/hgweb.py Mon Jun 13 18:36:40 2005 -0800
@@ -135,6 +135,7 @@
def refresh(self):
s = os.stat(os.path.join(self.path, ".hg", "00changelog.i"))
if s.st_mtime != self.mtime:
+ self.mtime = s.st_mtime
self.repo = repository(ui(), self.path)
def date(self, cs):
--- a/mercurial/mdiff.py Mon Jun 13 08:49:21 2005 +0100
+++ b/mercurial/mdiff.py Mon Jun 13 18:36:40 2005 -0800
@@ -43,28 +43,41 @@
def sortdiff(a, b):
la = lb = 0
-
+ lena = len(a)
+ lenb = len(b)
+
while 1:
- if la >= len(a) or lb >= len(b): break
- if b[lb] < a[la]:
- si = lb
- while lb < len(b) and b[lb] < a[la] : lb += 1
- yield "insert", la, la, si, lb
- elif a[la] < b[lb]:
- si = la
- while la < len(a) and a[la] < b[lb]: la += 1
- yield "delete", si, la, lb, lb
- else:
+ am, bm, = la, lb
+
+ # walk over matching lines
+ while lb < lenb and la < lena and a[la] == b[lb] :
la += 1
lb += 1
- if lb < len(b):
- yield "insert", la, la, lb, len(b)
+ if la > am:
+ yield (am, bm, la - am) # return a match
+
+ # skip mismatched lines from b
+ while lb < lenb and b[lb] < a[la]:
+ lb += 1
- if la < len(a):
- yield "delete", la, len(a), lb, lb
+ if lb >= lenb:
+ break
+
+ # skip mismatched lines from a
+ while la < lena and b[lb] > a[la]:
+ la += 1
+
+ if la >= lena:
+ break
+
+ yield (lena, lenb, 0)
def diff(a, b, sorted=0):
+ if not a:
+ s = "".join(b)
+ return s and (struct.pack(">lll", 0, 0, len(s)) + s)
+
bin = []
p = [0]
for i in a: p.append(p[-1] + len(i))
@@ -76,13 +89,16 @@
print a, b
raise
else:
- d = difflib.SequenceMatcher(None, a, b).get_opcodes()
-
- for o, m, n, s, t in d:
- if o == 'equal': continue
- s = "".join(b[s:t])
- bin.append(struct.pack(">lll", p[m], p[n], len(s)) + s)
-
+ d = difflib.SequenceMatcher(None, a, b).get_matching_blocks()
+ la = 0
+ lb = 0
+ for am, bm, size in d:
+ s = "".join(b[lb:bm])
+ if am > la or s:
+ bin.append(struct.pack(">lll", p[la], p[am], len(s)) + s)
+ la = am + size
+ lb = bm + size
+
return "".join(bin)
def patchtext(bin):
--- a/mercurial/revlog.py Mon Jun 13 08:49:21 2005 +0100
+++ b/mercurial/revlog.py Mon Jun 13 18:36:40 2005 -0800
@@ -43,17 +43,28 @@
indexformat = ">4l20s20s20s"
class lazyparser:
- def __init__(self, data):
+ def __init__(self, data, revlog):
self.data = data
self.s = struct.calcsize(indexformat)
self.l = len(data)/self.s
self.index = [None] * self.l
self.map = {nullid: -1}
+ self.all = 0
+ self.revlog = revlog
- def load(self, pos):
- block = pos / 1000
- i = block * 1000
- end = min(self.l, i + 1000)
+ def load(self, pos=None):
+ if self.all: return
+ if pos is not None:
+ block = pos / 1000
+ i = block * 1000
+ end = min(self.l, i + 1000)
+ else:
+ self.all = 1
+ i = 0
+ end = self.l
+ self.revlog.index = self.index
+ self.revlog.nodemap = self.map
+
while i < end:
d = self.data[i * self.s: (i + 1) * self.s]
e = struct.unpack(indexformat, d)
@@ -78,16 +89,14 @@
def __init__(self, parser):
self.p = parser
def load(self, key):
+ if self.p.all: return
n = self.p.data.find(key)
if n < 0: raise KeyError("node " + hex(key))
pos = n / self.p.s
self.p.load(pos)
def __contains__(self, key):
- try:
- self[key]
- return True
- except KeyError:
- return False
+ self.p.load()
+ return key in self.p.map
def __iter__(self):
for i in xrange(self.p.l):
try:
@@ -121,7 +130,7 @@
if len(i) > 10000:
# big index, let's parse it on demand
- parser = lazyparser(i)
+ parser = lazyparser(i, self)
self.index = lazyindex(parser)
self.nodemap = lazymap(parser)
else: