diff --git a/mercurial/ui.py b/mercurial/ui.py
--- a/mercurial/ui.py
+++ b/mercurial/ui.py
@@ -2197,6 +2197,9 @@ class paths(dict):
             loc, sub_opts = ui.configsuboptions(b'paths', name)
             self[name] = path(ui, name, rawloc=loc, suboptions=sub_opts)
 
+        for name, p in sorted(self.items()):
+            p.chain_path(ui, self)
+
     def getpath(self, ui, name, default=None):
         """Return a ``path`` from a string, falling back to default.
 
@@ -2331,6 +2334,22 @@ class path(object):
 
         self._apply_suboptions(ui, sub_opts)
 
+    def chain_path(self, ui, paths):
+        if self.url.scheme == b'path':
+            assert self.url.path is None
+            subpath = paths[self.url.host]
+            self.url = subpath.url
+            self.rawloc = subpath.rawloc
+            self.loc = subpath.loc
+            if self.branch is None:
+                self.branch = subpath.branch
+            else:
+                base = self.rawloc.rsplit(b'#', 1)[0]
+                self.rawloc = b'%s#%s' % (base, self.branch)
+            suboptions = subpath._all_sub_opts.copy()
+            suboptions.update(self._own_sub_opts)
+            self._apply_suboptions(ui, suboptions)
+
     def _validate_path(self):
         # When given a raw location but not a symbolic name, validate the
         # location is valid.
diff --git a/tests/test-paths.t b/tests/test-paths.t
--- a/tests/test-paths.t
+++ b/tests/test-paths.t
@@ -211,3 +211,126 @@ unknown sub-options aren't displayed
   000000000000
 
   $ cd ..
+
+Testing path referencing other paths
+====================================
+
+basic setup
+-----------
+
+  $ ls -1
+  a
+  b
+  gpath1
+  suboptions
+  $ hg init chained_path
+  $ cd chained_path
+  $ cat << EOF > .hg/hgrc
+  > [paths]
+  > default=../a
+  > other_default=path://default
+  > path_with_branch=../branchy#foo
+  > other_branch=path://path_with_branch
+  > other_branched=path://path_with_branch#default
+  > pushdest=../push-dest
+  > pushdest:pushrev=default
+  > pushdest2=path://pushdest
+  > pushdest-overwrite=path://pushdest
+  > pushdest-overwrite:pushrev=foo
+  > EOF
+
+  $ hg init ../branchy
+  $ hg init ../push-dest
+  $ hg debugbuilddag -R ../branchy '.:base+3<base@foo+5'
+  $ hg log -G -T '{branch}\n' -R ../branchy
+  o  foo
+  |
+  o  foo
+  |
+  o  foo
+  |
+  o  foo
+  |
+  o  foo
+  |
+  | o  default
+  | |
+  | o  default
+  | |
+  | o  default
+  |/
+  o  default
+  
+
+  $ hg paths
+  default = $TESTTMP/a
+  gpath1 = http://hg.example.com/
+  other_branch = $TESTTMP/branchy#foo
+  other_branched = $TESTTMP/branchy#default
+  other_default = $TESTTMP/a
+  path_with_branch = $TESTTMP/branchy#foo
+  pushdest = $TESTTMP/push-dest
+  pushdest:pushrev = default
+  pushdest-overwrite = $TESTTMP/push-dest
+  pushdest-overwrite:pushrev = foo
+  pushdest2 = $TESTTMP/push-dest
+  pushdest2:pushrev = default
+
+test basic chaining
+-------------------
+
+  $ hg path other_default
+  $TESTTMP/a
+  $ hg pull default
+  pulling from $TESTTMP/a
+  no changes found
+  $ hg pull other_default
+  pulling from $TESTTMP/a
+  no changes found
+
+test inheritance of the #fragment part
+--------------------------------------
+
+  $ hg pull path_with_branch
+  pulling from $TESTTMP/branchy
+  adding changesets
+  adding manifests
+  adding file changes
+  added 6 changesets with 0 changes to 0 files
+  new changesets 1ea73414a91b:bcebb50b77de
+  (run 'hg update' to get a working copy)
+  $ hg pull other_branch
+  pulling from $TESTTMP/branchy
+  no changes found
+  $ hg pull other_branched
+  pulling from $TESTTMP/branchy
+  searching for changes
+  adding changesets
+  adding manifests
+  adding file changes
+  added 3 changesets with 0 changes to 0 files (+1 heads)
+  new changesets 66f7d451a68b:2dc09a01254d
+  (run 'hg heads' to see heads)
+
+test inheritance of the suboptions
+----------------------------------
+
+  $ hg push pushdest
+  pushing to $TESTTMP/push-dest
+  searching for changes
+  adding changesets
+  adding manifests
+  adding file changes
+  added 4 changesets with 0 changes to 0 files
+  $ hg push pushdest2
+  pushing to $TESTTMP/push-dest
+  searching for changes
+  no changes found
+  [1]
+  $ hg push pushdest-overwrite --new-branch
+  pushing to $TESTTMP/push-dest
+  searching for changes
+  adding changesets
+  adding manifests
+  adding file changes
+  added 5 changesets with 0 changes to 0 files (+1 heads)