[fcm] 01/01: Upstream 2015.5.0

Alastair McKinstry mckinstry at moszumanska.debian.org
Mon Jun 15 11:24:38 UTC 2015


This is an automated email from the git hooks/post-receive script.

mckinstry pushed a commit to tag upstream_2015.5.0
in repository fcm.

commit 5a95f6405c835c9e926e3c1fb05999e9393fdbad
Author: Alastair McKinstry <mckinstry at debian.org>
Date:   Mon Jun 15 10:36:40 2015 +0100

    Upstream 2015.5.0
---
 CHANGES.md                                         |  144 +++
 CONTRIBUTING.md                                    |    1 +
 README.md                                          |    2 +-
 bin/fcm                                            |    2 +-
 bin/fcm_graphic_diff                               |    6 +-
 bin/fcm_graphic_merge                              |   23 +-
 bin/fcm_gui                                        |    2 +-
 bin/fcm_internal                                   |    2 +-
 bin/fcm_test_battery                               |    7 +-
 doc/collaboration/index.html                       |    2 +-
 doc/etc/fcm-terms-of-use.html                      |    2 +-
 doc/etc/fcm-version.js                             |    2 +-
 doc/etc/fcm.css                                    |    2 +-
 doc/etc/fcm.js                                     |    2 +-
 doc/index.html                                     |    2 +-
 doc/installation/index.html                        |    5 +-
 doc/release_notes/1-1.html                         |    2 +-
 doc/release_notes/1-2.html                         |    2 +-
 doc/release_notes/1-3.html                         |    2 +-
 doc/release_notes/1-4.html                         |    2 +-
 doc/release_notes/1-5.html                         |    2 +-
 doc/release_notes/2-0.html                         |    2 +-
 doc/release_notes/2-1.html                         |    2 +-
 doc/release_notes/2-2.html                         |    2 +-
 doc/release_notes/2-3-1.html                       |    2 +-
 doc/release_notes/2-3.html                         |    2 +-
 doc/release_notes/index.html                       |    2 +-
 doc/user_guide/annex_bld_cfg.html                  |    2 +-
 doc/user_guide/annex_cfg.html                      |   44 +-
 doc/user_guide/annex_ext_cfg.html                  |    2 +-
 doc/user_guide/annex_fcm_cfg.html                  |    2 +-
 doc/user_guide/annex_quick_ref.html                |    2 +-
 doc/user_guide/annex_quick_ref_tree_conflicts.html |    2 +-
 doc/user_guide/api.html                            |    2 +-
 doc/user_guide/build.html                          |    2 +-
 doc/user_guide/code_management.html                |    2 +-
 doc/user_guide/command_ref.html                    |   44 +-
 doc/user_guide/extract.html                        |    2 +-
 doc/user_guide/getting_started.html                |    2 +-
 doc/user_guide/index.html                          |    2 +-
 doc/user_guide/introduction.html                   |    2 +-
 doc/user_guide/make.html                           |  159 ++-
 doc/user_guide/overview.html                       |    2 +-
 doc/user_guide/system_admin.html                   |    2 +-
 doc/user_guide/working_practices.html              |    2 +-
 etc/svn-hooks/post-commit                          |    2 +-
 etc/svn-hooks/post-revprop-change                  |    2 +-
 etc/svn-hooks/pre-commit                           |    2 +-
 etc/svn-hooks/pre-revprop-change                   |    2 +-
 lib/FCM/Admin/Config.pm                            |    2 +-
 lib/FCM/Admin/Project.pm                           |    2 +-
 lib/FCM/Admin/Runner.pm                            |    2 +-
 lib/FCM/Admin/System.pm                            |   71 +-
 lib/FCM/Admin/User.pm                              |    2 +-
 lib/FCM/Admin/Users/LDAP.pm                        |    2 +-
 lib/FCM/Admin/Users/Passwd.pm                      |   34 +-
 lib/FCM/Admin/Util.pm                              |   13 +-
 lib/FCM/CLI.pm                                     |    2 +-
 lib/FCM/CLI/Exception.pm                           |    2 +-
 lib/FCM/CLI/Parser.pm                              |   17 +-
 lib/FCM/CLI/fcm-export-items.pod                   |    2 +-
 lib/FCM/CLI/fcm-make.pod                           |   21 +-
 lib/FCM/CLI/fcm-merge.pod                          |   10 +-
 lib/FCM/Class/CODE.pm                              |    2 +-
 lib/FCM/Class/Exception.pm                         |    2 +-
 lib/FCM/Class/HASH.pm                              |    2 +-
 lib/FCM/Context/ConfigEntry.pm                     |    2 +-
 lib/FCM/Context/Event.pm                           |    2 +-
 lib/FCM/Context/Keyword.pm                         |    2 +-
 lib/FCM/Context/Locator.pm                         |    2 +-
 lib/FCM/Context/Make.pm                            |    9 +-
 lib/FCM/Context/Make/Build.pm                      |    2 +-
 lib/FCM/Context/Make/Extract.pm                    |    2 +-
 lib/FCM/Context/Make/Mirror.pm                     |    2 +-
 lib/FCM/Context/Make/Share/Property.pm             |    2 +-
 lib/FCM/Context/Task.pm                            |    2 +-
 lib/FCM/Exception.pm                               |    2 +-
 lib/FCM/System.pm                                  |    2 +-
 lib/FCM/System/CM.pm                               |    8 +-
 lib/FCM/System/CM/CommitMessage.pm                 |    2 +-
 lib/FCM/System/CM/Prompt.pm                        |    2 +-
 lib/FCM/System/CM/ResolveConflicts.pm              |    2 +-
 lib/FCM/System/CM/SVN.pm                           |    8 +-
 lib/FCM/System/Exception.pm                        |    2 +-
 lib/FCM/System/Make.pm                             |   55 +-
 lib/FCM/System/Make/Build.pm                       |  120 +-
 lib/FCM/System/Make/Build/FileType.pm              |    2 +-
 lib/FCM/System/Make/Build/FileType/C.pm            |    2 +-
 lib/FCM/System/Make/Build/FileType/CPP.pm          |    2 +-
 lib/FCM/System/Make/Build/FileType/CXX.pm          |    2 +-
 lib/FCM/System/Make/Build/FileType/Data.pm         |    2 +-
 lib/FCM/System/Make/Build/FileType/FPP.pm          |    2 +-
 lib/FCM/System/Make/Build/FileType/Fortran.pm      |    2 +-
 lib/FCM/System/Make/Build/FileType/H.pm            |    2 +-
 lib/FCM/System/Make/Build/FileType/NS.pm           |    2 +-
 lib/FCM/System/Make/Build/FileType/Script.pm       |    2 +-
 lib/FCM/System/Make/Build/Task/Archive.pm          |    2 +-
 lib/FCM/System/Make/Build/Task/Compile.pm          |    2 +-
 lib/FCM/System/Make/Build/Task/Compile/C.pm        |    2 +-
 lib/FCM/System/Make/Build/Task/Compile/CXX.pm      |    2 +-
 lib/FCM/System/Make/Build/Task/Compile/Fortran.pm  |    2 +-
 lib/FCM/System/Make/Build/Task/ExtractInterface.pm |    6 +-
 lib/FCM/System/Make/Build/Task/Install.pm          |    2 +-
 lib/FCM/System/Make/Build/Task/Link.pm             |    2 +-
 lib/FCM/System/Make/Build/Task/Link/C.pm           |    2 +-
 lib/FCM/System/Make/Build/Task/Link/CXX.pm         |    2 +-
 lib/FCM/System/Make/Build/Task/Link/Fortran.pm     |    2 +-
 lib/FCM/System/Make/Build/Task/Preprocess.pm       |    2 +-
 lib/FCM/System/Make/Build/Task/Preprocess/C.pm     |    2 +-
 .../System/Make/Build/Task/Preprocess/Fortran.pm   |    2 +-
 lib/FCM/System/Make/Build/Task/Share.pm            |    2 +-
 lib/FCM/System/Make/Extract.pm                     |  166 ++-
 lib/FCM/System/Make/Mirror.pm                      |   34 +-
 lib/FCM/System/Make/Preprocess.pm                  |    2 +-
 lib/FCM/System/Make/Share/Config.pm                |   39 +-
 lib/FCM/System/Make/Share/Dest.pm                  |  139 ++-
 lib/FCM/System/Make/Share/Subsystem.pm             |    2 +-
 lib/FCM/System/Misc.pm                             |    2 +-
 lib/FCM/System/Old.pm                              |    2 +-
 lib/FCM/Util.pm                                    |    2 +-
 lib/FCM/Util/ConfigReader.pm                       |    2 +-
 lib/FCM/Util/ConfigUpgrade.pm                      |    2 +-
 lib/FCM/Util/Event.pm                              |    7 +-
 lib/FCM/Util/Exception.pm                          |    2 +-
 lib/FCM/Util/Locator.pm                            |    2 +-
 lib/FCM/Util/Locator/FS.pm                         |   15 +-
 lib/FCM/Util/Locator/SSH.pm                        |    6 +-
 lib/FCM/Util/Locator/SVN.pm                        |    2 +-
 lib/FCM/Util/Reporter.pm                           |    2 +-
 lib/FCM/Util/Shell.pm                              |    2 +-
 lib/FCM/Util/TaskRunner.pm                         |    2 +-
 lib/FCM1/Base.pm                                   |    2 +-
 lib/FCM1/Build.pm                                  |    2 +-
 lib/FCM1/Build/Fortran.pm                          |    2 +-
 lib/FCM1/BuildSrc.pm                               |    5 +-
 lib/FCM1/BuildTask.pm                              |    2 +-
 lib/FCM1/CfgFile.pm                                |   10 +-
 lib/FCM1/CfgLine.pm                                |    4 +-
 lib/FCM1/Cm.pm                                     |   39 +-
 lib/FCM1/CmBranch.pm                               |    2 +-
 lib/FCM1/CmUrl.pm                                  |    2 +-
 lib/FCM1/Config.pm                                 |    2 +-
 lib/FCM1/ConfigSystem.pm                           |    6 +-
 lib/FCM1/Dest.pm                                   |    2 +-
 lib/FCM1/Exception.pm                              |    2 +-
 lib/FCM1/Extract.pm                                |    2 +-
 lib/FCM1/ExtractConfigComparator.pm                |    2 +-
 lib/FCM1/ExtractFile.pm                            |    2 +-
 lib/FCM1/ExtractSrc.pm                             |    2 +-
 lib/FCM1/Interactive.pm                            |    2 +-
 lib/FCM1/Interactive/InputGetter.pm                |    2 +-
 lib/FCM1/Interactive/InputGetter/CLI.pm            |    2 +-
 lib/FCM1/Interactive/InputGetter/GUI.pm            |    2 +-
 lib/FCM1/Keyword.pm                                |    2 +-
 lib/FCM1/ReposBranch.pm                            |    2 +-
 lib/FCM1/SrcDirLayer.pm                            |    2 +-
 lib/FCM1/Timer.pm                                  |    2 +-
 lib/FCM1/Util.pm                                   |    2 +-
 lib/FCM1/Util/ClassLoader.pm                       |    2 +-
 man/man1/fcm.1                                     |    2 +-
 sbin/fcm-add-svn-repos                             |    2 +-
 sbin/fcm-add-svn-repos-and-trac-env                |    2 +-
 sbin/fcm-add-trac-env                              |    2 +-
 sbin/fcm-backup-svn-repos                          |    2 +-
 sbin/fcm-backup-trac-env                           |    2 +-
 sbin/fcm-commit-update                             |    2 +-
 sbin/fcm-daily-update                              |    2 +-
 sbin/fcm-install-svn-hook                          |    2 +-
 sbin/fcm-manage-trac-env-session                   |    2 +-
 sbin/fcm-manage-users                              |    2 +-
 sbin/fcm-recover-svn-repos                         |    2 +-
 sbin/fcm-recover-trac-env                          |    2 +-
 sbin/fcm-rpmbuild                                  |    2 +-
 sbin/fcm-user-to-email                             |    2 +-
 sbin/fcm-vacuum-trac-env-db                        |    2 +-
 sbin/my-regular-update.example                     |    2 +-
 sbin/post-commit-bg                                |   26 +-
 sbin/post-commit-bg-notify-who                     |   64 +-
 sbin/post-revprop-change-bg                        |    8 +-
 sbin/pre-commit                                    |    4 +-
 sbin/pre-commit-verify-branch-owner                |    2 +-
 sbin/pre-revprop-change                            |    2 +-
 sbin/svnperms.py                                   |    9 +-
 sbin/trac_hook                                     |    2 +-
 t/fcm-add-trac-env/00-basic.t                      |    2 +-
 t/fcm-add/00-simple.t                              |   15 +-
 t/fcm-add/test_header                              |    2 +-
 t/fcm-backup-svn-repos/00-basic.t                  |    2 +-
 t/fcm-branch-create/00-simple.t                    |    3 +-
 t/fcm-branch-create/test_header                    |    2 +-
 t/fcm-branch-delete/00-simple.t                    |    5 +-
 .../02-bad.t => fcm-branch-delete/01-bad-arg.t}    |   34 +-
 t/fcm-branch-delete/test_header                    |    2 +-
 t/fcm-branch-diff/00-simple.t                      |  455 ++------
 t/fcm-branch-diff/test_header                      |    2 +-
 t/fcm-branch-info/00-simple.t                      |    3 +-
 t/fcm-branch-info/test_header                      |    2 +-
 t/fcm-branch-list/00-simple.t                      |    3 +-
 t/fcm-branch-list/test_header                      |    2 +-
 .../27-args-only.t => fcm-build/00-geninterface.t} |   47 +-
 t/fcm-build/test_header                            |    1 +
 t/fcm-commit/00-simple.t                           |   59 +-
 t/fcm-commit/01-subtree.t                          |   60 +-
 t/fcm-commit/02-bad.t                              |    3 +-
 t/fcm-commit/03-message-file.t                     |    3 +-
 t/fcm-commit/{02-bad.t => 04-externals.t}          |   43 +-
 t/fcm-commit/test_header                           |    2 +-
 t/fcm-conflicts/00-tree-add-add.t                  |    3 +-
 t/fcm-conflicts/01-tree-delete-delete.t            |    3 +-
 t/fcm-conflicts/02-tree-delete-edit.t              |    3 +-
 t/fcm-conflicts/03-tree-delete-rename.t            |    3 +-
 t/fcm-conflicts/04-tree-edit-delete.t              |    3 +-
 t/fcm-conflicts/05-tree-edit-rename.t              |    3 +-
 t/fcm-conflicts/06-tree-rename-delete.t            |    3 +-
 t/fcm-conflicts/07-tree-rename-edit.t              |    3 +-
 t/fcm-conflicts/08-tree-rename-rename-diff.t       |    3 +-
 t/fcm-conflicts/09-tree-rename-rename-same.t       |    3 +-
 t/fcm-conflicts/10-text.t                          |   54 +-
 t/fcm-conflicts/test_header                        |    2 +-
 t/fcm-diff/00-simple.t                             |  105 +-
 t/fcm-diff/test_header                             |    2 +-
 t/fcm-install-svn-hook/00-basic.t                  |    6 +-
 t/fcm-install-svn-hook/01-housekeep-log.t          |    2 +-
 t/fcm-install-svn-hook/02-env.t                    |    2 +-
 t/fcm-install-svn-hook/test_header_more            |    2 +-
 t/fcm-keyword-print/00-simple.t                    |    2 +-
 t/fcm-loc-layout/00-simple.t                       |    2 +-
 t/fcm-loc-layout/test_header                       |    2 +-
 t/fcm-make/00-build-basic.t                        |    2 +-
 t/fcm-make/00-build-basic/bin/my-ld                |    2 +-
 t/fcm-make/01-build-link-opts.t                    |    2 +-
 t/fcm-make/02-build-ext-iface.t                    |    2 +-
 .../02-build-ext-iface/expected/t1.interface       |    6 +
 t/fcm-make/02-build-ext-iface/src/t1.f90           |   14 +
 t/fcm-make/03-build-include-paths.t                |    2 +-
 t/fcm-make/04-build-libs.t                         |    2 +-
 t/fcm-make/05-build-c-cxx-basic.t                  |    2 +-
 t/fcm-make/06-extract-ssh.t                        |    2 +-
 t/fcm-make/07-build-ns-dep.t                       |    4 +-
 t/fcm-make/08-build-dup-dep.t                      |    4 +-
 t/fcm-make/09-build-dep-o.t                        |   10 +-
 t/fcm-make/10-log.t                                |   16 +-
 t/fcm-make/11-preprocess-include-path.t            |    2 +-
 t/fcm-make/12-build-class-prop.t                   |    2 +-
 t/fcm-make/13-build-target-prop.t                  |    2 +-
 t/fcm-make/13-build-target-prop/bin/my-fc          |    2 +-
 t/fcm-make/14-build-etc.t                          |    4 +-
 t/fcm-make/15-extract-loc-reset.t                  |    2 +-
 t/fcm-make/16-build-dep-o-2.t                      |    4 +-
 t/fcm-make/17-build-cyclic.t                       |    4 +-
 t/fcm-make/18-build-use-intrinsic.t                |    4 +-
 t/fcm-make/19-build-inherit-prop.t                 |    2 +-
 t/fcm-make/20-args.t                               |    2 +-
 t/fcm-make/21-inherit-steps.t                      |    2 +-
 t/fcm-make/22-build-2-bad-mod-over-inherit.t       |    2 +-
 t/fcm-make/23-build-omp.t                          |    2 +-
 t/fcm-make/24-build-c-main-camel.t                 |    2 +-
 t/fcm-make/25-build-cyclic-2.t                     |    2 +-
 t/fcm-make/26-no-config.t                          |    2 +-
 t/fcm-make/27-args-only.t                          |    2 +-
 t/fcm-make/28-bad-arg.t                            |    2 +-
 t/fcm-make/29-relative-cfg.t                       |    2 +-
 t/fcm-make/30-relative-cfg-in-svn.t                |    2 +-
 t/fcm-make/31-relative-cfg-in-ssh.t                |    2 +-
 t/fcm-make/32-include-relative-cfg.t               |    2 +-
 t/fcm-make/33-include-relative-cfg-in-svn.t        |    2 +-
 t/fcm-make/34-include-relative-cfg-in-ssh.t        |    2 +-
 t/fcm-make/35-include-relative-cfg-in-2-dirs.t     |    2 +-
 t/fcm-make/36-build-fail-cont-basic.t              |   13 +-
 .../{26-no-config.t => 37-no-such-config-file.t}   |    8 +-
 t/fcm-make/38-extract-inherit-set-primary.t        |   79 ++
 ...e-relative-cfg.t => 39-build-source-with-dot.t} |   54 +-
 ...in-2-dirs.t => 40-extract-fs-source-with-dot.t} |   75 +-
 t/fcm-make/41-ctx-name.t                           |  177 +++
 t/fcm-make/42-make-mirror-make2.t                  |  125 ++
 t/fcm-make/43-ctx-name-inherit.t                   |   98 ++
 t/fcm-make/44-ctx-name-inherit-compat.t            |   92 ++
 t/fcm-make/45-dest-mv.t                            |   85 ++
 t/fcm-make/46-archive-mode.t                       |  111 ++
 t/fcm-merge/00-simple.t                            |  235 ++--
 t/fcm-merge/01-complex.t                           | 1192 +++++++++-----------
 t/fcm-merge/02-reverse.t                           |  135 +++
 t/fcm-merge/test_header                            |   40 +-
 t/fcm-recover-svn-repos/00-basic.t                 |    2 +-
 t/fcm-status/00-simple.t                           |   26 +-
 t/fcm-status/test_header                           |    2 +-
 t/fcm-switch/00-simple.t                           |   65 +-
 t/fcm-switch/01-subtree.t                          |   92 +-
 t/fcm-switch/test_header                           |    2 +-
 t/fcm-update/00-simple.t                           |   84 +-
 t/fcm-update/01-subtree.t                          |   83 +-
 t/fcm-update/test_header                           |    2 +-
 t/lib/bash/test_header                             |   86 +-
 t/svn-hooks/00-pre-revprop-change.t                |    2 +-
 t/svn-hooks/01-post-revprop-change-bg.t            |    2 +-
 t/svn-hooks/02-pre-commit.t                        |    5 +-
 t/svn-hooks/03-post-commit-bg.t                    |   88 +-
 t/svn-hooks/04-svnperms.t                          |  121 ++
 t/svn-hooks/test_header_more                       |    7 +-
 t/svn-username/00-branch.t                         |    2 +-
 t/svn-username/test_header                         |    2 +-
 tutorial/fcm-tutorial-repos-create                 |    2 +-
 usr/bin/fcm                                        |    2 +-
 303 files changed, 3564 insertions(+), 2403 deletions(-)

diff --git a/CHANGES.md b/CHANGES.md
index 57df69a..485ca1a 100644
--- a/CHANGES.md
+++ b/CHANGES.md
@@ -5,6 +5,150 @@ for a full listing of issues for each release.
 
 --------------------------------------------------------------------------------
 
+## 2015.05.0 (2015-05-28)
+
+FCM release 25.
+
+### Highlighted Changes
+
+[#188](https://github.com/metomi/fcm/pull/188):
+fcm make: allow multiple runs in same directory. A make can now be named, so
+multiple non-overlapping makes can work in the same directory. It is worth
+noting that once you have used this version of `fcm make` on a directory, older
+version of FCM will no longer work in incremental mode on the same directory.
+See also [metomi/rose#1604](https://github.com/metomi/rose/pull/1604).
+
+### Noteworthy Changes
+
+[#190](https://github.com/metomi/fcm/pull/190):
+fcm make: new `--archive` option. If archive mode is specified, TAR-GZIP these
+items by default:
+* `.fcm-make/cache/extract/`
+* `build/include/`
+* `build/o/`
+
+where `extract` and `build` are names of extract and build steps.
+Users can configure what to TAR-GZIP under `build/`.
+
+[#189](https://github.com/metomi/fcm/pull/189):
+fcm make: correctly support relocation of a make.
+
+--------------------------------------------------------------------------------
+
+## 2015.03.0 (2015-03-26)
+
+FCM release 24.
+
+### Noteworthy Changes
+
+[#183](https://github.com/metomi/fcm/pull/183):
+Use of Subversion 1.6 with FCM is no longer recommended.
+
+[#181](https://github.com/metomi/fcm/pull/181):
+fcm make: source file find: ignore hidden paths only if paths are under
+the source root directory, i.e. it is now OK for the source root directory to
+be a hidden path itself.
+
+[#178](https://github.com/metomi/fcm/pull/178):
+fcm make: `.fcm-make/log` symbolic links are now relative. This should make it
+easier to relocate a build.
+
+--------------------------------------------------------------------------------
+
+## 2015.02.0 (2015-02-10)
+
+FCM release 23.
+
+### Noteworthy Changes
+
+[#176](https://github.com/metomi/fcm/pull/176):
+fcm make: build: fix creation of Fortran interface files where procedure
+arguments declared with `EXTERNAL` statements were incorrectly matched in
+case-sensitive mode.
+
+[#170](https://github.com/metomi/fcm/pull/170):
+fcm commit: now works in a working copy with *externals*.
+
+[#169](https://github.com/metomi/fcm/pull/169):
+fcm branch-delete: now fails if bad arguments specified.
+
+[#168](https://github.com/metomi/fcm/pull/168):
+fcm branch-diff: `--trac` now works correctly. The `/intertrac/` syntax did not
+appear to work any more. Use `/search?q=` syntax instead.
+
+--------------------------------------------------------------------------------
+
+## 2014.12.0 (2014-12-08)
+
+FCM release 22.
+
+### Noteworthy Changes
+
+[#164](https://github.com/metomi/fcm/pull/164):
+fcm build: fix fortran interface generation, broken by
+[#156](https://github.com/metomi/fcm/pull/156).
+
+[#163](https://github.com/metomi/fcm/pull/163):
+fcm merge --reverse: improve logic. It now works with non-standard layout. The
+`--revision=[M:]N` option is no longer compulsory. It now uses the last changed
+revision of the working copy by default.
+
+[#162](https://github.com/metomi/fcm/pull/162):
+fcm-manage-trac-env-session: fix session logic. If a user already has some
+entries in the `session_attribute` table, the old logic will not insert a new
+`name` or `email` for the user. The new logic will only skip the `name` or
+`email` attribute if already set correctly.
+
+--------------------------------------------------------------------------------
+
+## 2014.11.0 (2014-11-25)
+
+FCM release 21.
+
+### Noteworthy Changes
+
+[#161](https://github.com/metomi/fcm/pull/161):
+post-commit-bg-notify-who: use branch creator as branch owner if it cannot be
+determined by the branch name.
+
+[#159](https://github.com/metomi/fcm/pull/159),
+[#160](https://github.com/metomi/fcm/pull/160):
+FCM's Subversion wrappers: display error messages when `svn info` commands
+fail.
+
+[#158](https://github.com/metomi/fcm/pull/158):
+fcm make: extract: improve checking of primary location in inherited mode.
+Compare old value with normalised version of new value. E.g. use of location
+keywords and extra slashes at the end of the path will no longer result in a
+configuration conflict.
+
+[#156](https://github.com/metomi/fcm/pull/156):
+fcm extract and fcm build: fix warnings from Perl 5.12+ when parsing
+configuration file.
+
+[#155](https://github.com/metomi/fcm/pull/155):
+fcm make: fix report of no such config file.
+
+[#150](https://github.com/metomi/fcm/pull/150):
+fcm-manage-trac-env-session: improve removal logic.
+
+[#149](https://github.com/metomi/fcm/pull/149):
+svnperms.py: fix bug, alter message override, and add tests.
+
+[#148](https://github.com/metomi/fcm/pull/148):
+Reverse `commit.conf` logic. To verify branch owner, specify
+`verify-branch-owner`.  To notify branch owner, specify `notify-owner`.
+`post-commit-bg` now supports owner notification on trunk commit.
+
+[#147](https://github.com/metomi/fcm/pull/147):
+Use `dd conv=fsync` to create backup and dump to ensure that backup and dump
+data is written to disk before returning a good status.
+
+[#146](https://github.com/metomi/fcm/pull/146):
+fcm merge: basic support for `meld`.
+
+--------------------------------------------------------------------------------
+
 ## 2014.09.0 (2014-09-17)
 
 FCM release 20.
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index abd2140..214f9c6 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -29,6 +29,7 @@ below:
 * Stephen Oxley (Met Office, UK)
 * Matt Shin (Met Office, UK)
 * Matt Pryor (Met Office, UK)
+* Roddy Sharp (Met Office, UK)
 
 (All contributors are identifiable with email addresses in the version
 control logs or otherwise.)
diff --git a/README.md b/README.md
index bed2f5e..4748829 100644
--- a/README.md
+++ b/README.md
@@ -9,7 +9,7 @@ and wrappers to Subversion for scientific software development
 
 ## Copyright and Terms of Use
 
-(C) British Crown Copyright 2006-14 Met Office.
+(C) British Crown Copyright 2006-15 Met Office.
 
 FCM is free software: you can redistribute it and/or modify
 it under the terms of the GNU General Public License as published by
diff --git a/bin/fcm b/bin/fcm
index 58c2c74..e6c6989 100755
--- a/bin/fcm
+++ b/bin/fcm
@@ -1,6 +1,6 @@
 #!/usr/bin/env perl
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/bin/fcm_graphic_diff b/bin/fcm_graphic_diff
index a867d0d..8038ea2 100755
--- a/bin/fcm_graphic_diff
+++ b/bin/fcm_graphic_diff
@@ -1,6 +1,6 @@
 #!/usr/bin/env perl
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -35,6 +35,7 @@ my %S = (
 my %LABELS_HANDLER_FOR = (
     'tkdiff' => sub {map {('-L', $_)} @_},
     'xxdiff' => sub {('--title1', $_[0], '--title2', $_[1])},
+    'meld'   => sub {map {('-L', $_)} @_},
 );
 
 if (!caller()) {
@@ -115,10 +116,11 @@ If OLD_LABEL and NEW_LABEL are set, they are printed in the format:
     ++++ NEW_LABEL
 
 The command makes use of the labels when the diff command is either
-L<xxdiff|xxdiff> or L<tkdiff|tkdiff>:
+L<xxdiff|xxdiff>, L<tkdiff|tkdiff>, or L<meld|meld>:
 
     xxdiff --title1 OLD_LABEL --title2 NEW_LABEL OLD NEW
     tkdiff -L OLD_LABEL -L NEW_LABEL OLD NEW
+    meld   -L OLD_LABEL -L NEW_LABEL OLD NEW
 
 The command returns 0 if the files are the same or 1 if the files differ. All
 other return codes should be regarded as fatal errors.
diff --git a/bin/fcm_graphic_merge b/bin/fcm_graphic_merge
index 6e4043f..612c915 100755
--- a/bin/fcm_graphic_merge
+++ b/bin/fcm_graphic_merge
@@ -1,6 +1,6 @@
 #!/usr/bin/env perl
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -23,6 +23,7 @@ use warnings;
 
 my %IMPL = ('fcm-dummy-diff' => \&_fcm_dummy_diff,
             'xxdiff' => \&_xxdiff,
+            'meld'   => \&_meld,
             'kdiff3' => \&_kdiff3);
 
 my %UNRESOLVED = (
@@ -93,6 +94,23 @@ sub _kdiff3 {
     return 0;
 }
 
+sub _meld {
+    my ($base, $mine, $older, $yours) = @_;
+    # Not using --auto-merge option as it alters the middle pane before user
+    # can review changes.
+    my @command = (qw{meld -a -o}, $base, $mine, $older, $yours);
+    my @out_lines = qx{@command};
+    my $rc = $?;
+    # meld doesn't produce any output, so we just assume a non-zero
+    # exit code means unresolved merges
+    if ($rc) {
+        print($UNRESOLVED{'merged'});
+        return 1;
+    }
+    printf("You merged all the changes.\n");
+    return 0;
+}
+
 __END__
 
 =head1 NAME
@@ -105,6 +123,9 @@ fcm_graphic_merge
 
 =head1 DESCRIPTION
 
+Invokes L<xxdiff|xxdiff> (or the command specified in the FCM_GRAPHIC_MERGE
+environment variable) to compare the CURRENT, ANCESTOR and NEW files, where possible.
+
 Wrap L<xxdiff|xxdiff>. Invoke L<xxdiff|xxdiff> as:
 
     xxdiff -m -M BASE -O -X MINE OLDER YOURS
diff --git a/bin/fcm_gui b/bin/fcm_gui
index e1f2210..0c01192 100755
--- a/bin/fcm_gui
+++ b/bin/fcm_gui
@@ -1,6 +1,6 @@
 #!/usr/bin/env perl
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/bin/fcm_internal b/bin/fcm_internal
index 809a19e..12e5bc2 100755
--- a/bin/fcm_internal
+++ b/bin/fcm_internal
@@ -1,6 +1,6 @@
 #!/usr/bin/env perl
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/bin/fcm_test_battery b/bin/fcm_test_battery
index 2ac1a6a..6900563 100755
--- a/bin/fcm_test_battery
+++ b/bin/fcm_test_battery
@@ -1,6 +1,6 @@
 #!/usr/bin/env bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,4 +21,7 @@ cd $(dirname $0)/..
 if [[ "$PWD" != "$OLDPWD" ]]; then
     echo "[INFO] cd $PWD"
 fi
-exec prove -j 9 -s -r "${@:-t}"
+if [[ -f '/proc/cpuinfo' ]]; then
+    NPROC="$(grep -ic 'processor' '/proc/cpuinfo')"
+fi
+exec prove -j "${NPROC:-9}" -s -r "${@:-t}"
diff --git a/doc/collaboration/index.html b/doc/collaboration/index.html
index cfabe81..a422bf2 100644
--- a/doc/collaboration/index.html
+++ b/doc/collaboration/index.html
@@ -463,7 +463,7 @@ patch -p0 < my_patchfile
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/etc/fcm-terms-of-use.html b/doc/etc/fcm-terms-of-use.html
index a7316bd..184f2dd 100644
--- a/doc/etc/fcm-terms-of-use.html
+++ b/doc/etc/fcm-terms-of-use.html
@@ -78,7 +78,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.<br />
       This document is released under the British <a href=
       "http://www.nationalarchives.gov.uk/doc/open-government-licence/" rel=
diff --git a/doc/etc/fcm-version.js b/doc/etc/fcm-version.js
index ca077f8..bdab405 100644
--- a/doc/etc/fcm-version.js
+++ b/doc/etc/fcm-version.js
@@ -1 +1 @@
-FCM.VERSION="2014.09.0";
+FCM.VERSION="2015.05.0";
diff --git a/doc/etc/fcm.css b/doc/etc/fcm.css
index c25e6c7..c187c7e 100644
--- a/doc/etc/fcm.css
+++ b/doc/etc/fcm.css
@@ -1,5 +1,5 @@
 /**********************************************************************
- * (C) British Crown Copyright 2006-14 Met Office.
+ * (C) British Crown Copyright 2006-15 Met Office.
  *
  * This file is part of FCM.
  *
diff --git a/doc/etc/fcm.js b/doc/etc/fcm.js
index 1a6ccef..e0a7b8a 100644
--- a/doc/etc/fcm.js
+++ b/doc/etc/fcm.js
@@ -1,5 +1,5 @@
 /**********************************************************************
- * (C) British Crown Copyright 2006-14 Met Office.
+ * (C) British Crown Copyright 2006-15 Met Office.
  *
  * This file is part of FCM.
  *
diff --git a/doc/index.html b/doc/index.html
index 6d73ef7..500ce3c 100644
--- a/doc/index.html
+++ b/doc/index.html
@@ -75,7 +75,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/installation/index.html b/doc/installation/index.html
index 2b25aef..d2c3f01 100644
--- a/doc/installation/index.html
+++ b/doc/installation/index.html
@@ -112,8 +112,7 @@
       <p><dfn>used by:</dfn> the code management commands, the extract system
       of <code>fcm make</code>, the deprecated <code>fcm extract</code>.</p>
 
-      <p><dfn>versions known to work:</dfn> AIX-7: 1.6.18, RHEL-6: 1.6.17,
-      RHEL-6: 1.8.8.</p>
+      <p><dfn>versions known to work:</dfn>RHEL-6: 1.8.10.</p>
 
       <p><dfn>remark:</dfn> you can use the extract system to mirror code to a
       remote platform for building. Therefore it is only necessary to have
@@ -336,7 +335,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/release_notes/1-1.html b/doc/release_notes/1-1.html
index a66ab78..54f9af8 100644
--- a/doc/release_notes/1-1.html
+++ b/doc/release_notes/1-1.html
@@ -457,7 +457,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/release_notes/1-2.html b/doc/release_notes/1-2.html
index e8824d7..8dca12a 100644
--- a/doc/release_notes/1-2.html
+++ b/doc/release_notes/1-2.html
@@ -382,7 +382,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/release_notes/1-3.html b/doc/release_notes/1-3.html
index f9dc901..a36cc90 100644
--- a/doc/release_notes/1-3.html
+++ b/doc/release_notes/1-3.html
@@ -567,7 +567,7 @@ fcm bld
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/release_notes/1-4.html b/doc/release_notes/1-4.html
index 7616f76..fe8c073 100644
--- a/doc/release_notes/1-4.html
+++ b/doc/release_notes/1-4.html
@@ -377,7 +377,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/release_notes/1-5.html b/doc/release_notes/1-5.html
index b7de61b..940094c 100644
--- a/doc/release_notes/1-5.html
+++ b/doc/release_notes/1-5.html
@@ -465,7 +465,7 @@ Tk::ROText
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/release_notes/2-0.html b/doc/release_notes/2-0.html
index 976d4e5..3c99128 100644
--- a/doc/release_notes/2-0.html
+++ b/doc/release_notes/2-0.html
@@ -736,7 +736,7 @@ extract.location{diff}[um] = \
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/release_notes/2-1.html b/doc/release_notes/2-1.html
index c33bf7d..0fd8540 100644
--- a/doc/release_notes/2-1.html
+++ b/doc/release_notes/2-1.html
@@ -439,7 +439,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/release_notes/2-2.html b/doc/release_notes/2-2.html
index 6198d6b..de8af6d 100644
--- a/doc/release_notes/2-2.html
+++ b/doc/release_notes/2-2.html
@@ -582,7 +582,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/release_notes/2-3-1.html b/doc/release_notes/2-3-1.html
index 8b6e92c..7641d17 100644
--- a/doc/release_notes/2-3-1.html
+++ b/doc/release_notes/2-3-1.html
@@ -99,7 +99,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/release_notes/2-3.html b/doc/release_notes/2-3.html
index da5e9b2..db98ea2 100644
--- a/doc/release_notes/2-3.html
+++ b/doc/release_notes/2-3.html
@@ -118,7 +118,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/release_notes/index.html b/doc/release_notes/index.html
index a1ec0b9..3418c9e 100644
--- a/doc/release_notes/index.html
+++ b/doc/release_notes/index.html
@@ -87,7 +87,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/annex_bld_cfg.html b/doc/user_guide/annex_bld_cfg.html
index 9e15477..84eef05 100644
--- a/doc/user_guide/annex_bld_cfg.html
+++ b/doc/user_guide/annex_bld_cfg.html
@@ -913,7 +913,7 @@ outfile_ext::interface  .foo
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/annex_cfg.html b/doc/user_guide/annex_cfg.html
index 8f6fb9b..a6c7afc 100644
--- a/doc/user_guide/annex_cfg.html
+++ b/doc/user_guide/annex_cfg.html
@@ -521,6 +521,23 @@ dest = $HERE
 </pre>
     </dd>
 
+    <dt id="make.name">name</dt>
+
+    <dd>
+      <p><dfn>description</dfn>: Specifies the NAME of the make, so that the
+      command will search for <q>fcm-make<var>NAME</var>.cfg</q> instead of
+      <q>fcm-make.cfg</q>, and will write context files in
+      <q>.fcm-make<var>NAME</var>/</q> and log files as
+      <q>fcm-make<var>NAME</var>.log</q>, etc.</p>
+
+      <p><dfn>value</dfn>: A file name friendly string.</p>
+
+      <p><dfn>example</dfn>:</p>
+      <pre>
+name = -friend
+</pre>
+    </dd>
+
     <dt id="make.steps">steps</dt>
 
     <dd>
@@ -761,8 +778,14 @@ extract.prop{diff3.flags} = -E -m
       <p><dfn>example</dfn>:</p>
       <pre>
 mirror.target = fred at server:/path/of/dest
+
 # Or if the current user ID is "fred"
+# Or if the user ID for "server" is configured under "~/.ssh/config"
 mirror.target = server:/path/of/dest
+
+# Or if mirroring to a path accessible only by user ID "bob"
+mirror.target = bob at localhost:/path/of/dest
+
 # Or if the current user ID is "fred" and local host is "server"
 mirror.target = /path/of/dest
 </pre>
@@ -788,6 +811,11 @@ mirror.prop{rsync} = cnysr
   <code>mirror.prop</code> declaration:</p>
 
   <dl>
+    <dt id="make.mirror.prop.config-file.name">config-file.name</dt>
+
+    <dd>The context name to be included in the generated configuration file in
+    the mirror destination.</dd>
+
     <dt id="make.mirror.prop.config-file.steps">config-file.steps</dt>
 
     <dd>The steps to be included in the generated configuration file in the
@@ -944,8 +972,22 @@ build.prop{fc.libs}[myprog.exe] = netcdf grib
 
     <dt id="make.build.prop.ar.flags">ar.flags</dt>
 
+    <dd>If a list of values is specified, the system will not inherit sources
+    with the name-spaces matching the specified values. If the value is a
+    <samp>*</samp>, the system will not inherit any sources.</dd>
     <dd>The options used by the archive command. (default=<samp>rs</samp>)</dd>
 
+    <dt id=
+    "make.build.prop.archive-ok-target-category">archive-ok-target-category
+    *</dt>
+
+    <dd>If <code>fcm make</code> is invoked with the <code>--archive</code>
+    option, sub-directories in categories containing intermediate build files
+    will be put into TAR-GZIP files. E.g. with the default setting,
+    <samp>include/</samp> and <samp>o/</samp> will become
+    <samp>include.tar.gz</samp> and <samp>o.tar.gz</samp> respectively.
+    (default=<samp>include o</samp>)</dd>
+
     <dt id="make.build.prop.cc">cc</dt>
 
     <dd>The C compiler and linker. (default=<samp>gcc</samp>)</dd>
@@ -1415,7 +1457,7 @@ build.prop{fc.libs}[myprog.exe] = netcdf grib
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/annex_ext_cfg.html b/doc/user_guide/annex_ext_cfg.html
index f56fca7..6bb7fed 100644
--- a/doc/user_guide/annex_ext_cfg.html
+++ b/doc/user_guide/annex_ext_cfg.html
@@ -379,7 +379,7 @@ bld::tool::cc sxmpic++
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/annex_fcm_cfg.html b/doc/user_guide/annex_fcm_cfg.html
index f5d25b9..ea86344 100644
--- a/doc/user_guide/annex_fcm_cfg.html
+++ b/doc/user_guide/annex_fcm_cfg.html
@@ -180,7 +180,7 @@ set::url_browser_mapping::var::browser_rev_template @{1}
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/annex_quick_ref.html b/doc/user_guide/annex_quick_ref.html
index be921cc..1aa0b0e 100644
--- a/doc/user_guide/annex_quick_ref.html
+++ b/doc/user_guide/annex_quick_ref.html
@@ -238,7 +238,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/annex_quick_ref_tree_conflicts.html b/doc/user_guide/annex_quick_ref_tree_conflicts.html
index 3cd2f99..072ff38 100644
--- a/doc/user_guide/annex_quick_ref_tree_conflicts.html
+++ b/doc/user_guide/annex_quick_ref_tree_conflicts.html
@@ -265,7 +265,7 @@ A   +   FILENAME
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/api.html b/doc/user_guide/api.html
index 9913835..756bc69 100644
--- a/doc/user_guide/api.html
+++ b/doc/user_guide/api.html
@@ -204,7 +204,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/build.html b/doc/user_guide/build.html
index 12ec032..92d649f 100644
--- a/doc/user_guide/build.html
+++ b/doc/user_guide/build.html
@@ -1628,7 +1628,7 @@ egg/fried.h
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/code_management.html b/doc/user_guide/code_management.html
index 20352a3..1049570 100644
--- a/doc/user_guide/code_management.html
+++ b/doc/user_guide/code_management.html
@@ -1225,7 +1225,7 @@ Merge succeeded.
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/command_ref.html b/doc/user_guide/command_ref.html
index efc3426..185eb0f 100644
--- a/doc/user_guide/command_ref.html
+++ b/doc/user_guide/command_ref.html
@@ -1155,7 +1155,7 @@ browser = konqueror
         <dd>Specifies the path to the destination.
         (default=<samp>$PWD</samp>)</dd>
 
-        <dt><code>--new</code></dt>
+        <dt><code>--new</code>, <code>-N</code></dt>
 
         <dd>Specifies the new mode. In this mode, everything is re-exported.
         Otherwise, the system runs in incremental mode, in which the version
@@ -1334,6 +1334,17 @@ browser = konqueror
 
     <dd>
       <dl>
+        <dt><code>--archive, -a</code></dt>
+
+        <dd>Switch on archive mode. In archive mode, intermediate files will be
+        put into TAR-GZIP archives on completion, e.g. extract system:
+        <samp>.fcm-make/cache/extract/</samp>, and build system:
+        <samp>build/include/</samp> and <samp>build/o/</samp>.
+
+          <p>The archive mode is not suitable for a make that will be inherited
+          or used by other makes.</p>
+        </dd>
+
         <dt><code>--config-file-path=PATH, -F PATH</code></dt>
 
         <dd>Specifies paths for searching configuration files specified in
@@ -1347,9 +1358,8 @@ browser = konqueror
 
         <dt><code>--directory=PATH, -C PATH</code></dt>
 
-        <dd>Specifies the path to the destination. (default=<samp>$PWD</samp>
-        or whatever is specified in the <code>dest</code> setting in the
-        configuration file)</dd>
+        <dd>Change directory to <var>PATH</var> before doing anything.
+        (default=<var>$PWD</var>)</dd>
 
         <dt><code>--ignore-lock</code></dt>
 
@@ -1364,7 +1374,14 @@ browser = konqueror
         <dd>Specifies the number of (child) processes that can be run
         simultaneously.</dd>
 
-        <dt><code>--new</code></dt>
+        <dt><code>--name=NAME</code>, <code>-n NAME</code></dt>
+
+        <dd>Specify a name for the make, so that the command will search for
+        <q>fcm-make<var>NAME</var>.cfg</q> instead of <q>fcm-make.cfg</q>, and
+        will write context files in <q>.fcm-make<var>NAME</var>/</q> and log
+        files as <q>fcm-make<var>NAME</var>.log</q>, etc.</dd>
+
+        <dt><code>--new</code>, <code>-N</code></dt>
 
         <dd>Removes items in the destination created by the previous make, and
         starts a new make.</dd>
@@ -1388,7 +1405,7 @@ browser = konqueror
     <dd><code>fcm merge [OPTIONS] SOURCE</code><br />
     <code>fcm merge --custom --revision N[:M] [OPTIONS] SOURCE</code><br />
     <code>fcm merge --custom [OPTIONS] URL1[@REV1] URL2[@REV2]</code><br />
-    <code>fcm merge --reverse --revision [M:]N [OPTIONS]</code></dd>
+    <code>fcm merge --reverse [--revision [M:]N] [OPTIONS]</code></dd>
 
     <dt>Description</dt>
 
@@ -1519,13 +1536,12 @@ browser = konqueror
 
         <dd>
           <p>The reverse mode is useful if you need to reverse a changeset (or
-          a range of changesets) in the current source of the working copy. In
-          this mode, you must specify a revision (range) using the
-          <code>--revision</code> option. If you specify a single revision
-          <var>N</var>, the merge delta is between revision <var>N</var> and
-          revision <var>N - 1</var> of the current branch. Otherwise, the merge
-          delta is between revision <var>M</var> and revision <var>N</var>,
-          where <var>M</var> > <var>N</var>.</p>
+          a range of changesets) in the current source of the working copy. If
+          a revision is not specified with <code>--revision=M:N</code>, it
+          attempts to merge the delta <var>COMMITTED:(COMMITTED - 1)</var>. If
+          a single revision <var>N</var> is specified, the merge delta is
+          <var>N:(N - 1)</var>.  Otherwise, the merge delta is between revision
+          <var>M:N</var>, where <var>M</var> > <var>N</var>.</p>
 
           <p>N.B. Like custom merges, reverse merges are not tracked or used by
           subsequent FCM <code>diff</code> or <code>merge</code> commands,
@@ -1987,7 +2003,7 @@ browser = konqueror
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/extract.html b/doc/user_guide/extract.html
index ca04f0e..b9f4c2b 100644
--- a/doc/user_guide/extract.html
+++ b/doc/user_guide/extract.html
@@ -1153,7 +1153,7 @@ bld::tool::fflags::bar    -w %bld::tool::fflags
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/getting_started.html b/doc/user_guide/getting_started.html
index 26d02f4..83545b5 100644
--- a/doc/user_guide/getting_started.html
+++ b/doc/user_guide/getting_started.html
@@ -1472,7 +1472,7 @@ Committed revision 813.
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/index.html b/doc/user_guide/index.html
index 593f06e..2eea571 100644
--- a/doc/user_guide/index.html
+++ b/doc/user_guide/index.html
@@ -84,7 +84,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/introduction.html b/doc/user_guide/introduction.html
index d5fad9f..80761e6 100644
--- a/doc/user_guide/introduction.html
+++ b/doc/user_guide/introduction.html
@@ -97,7 +97,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/make.html b/doc/user_guide/make.html
index f4d3fee..9d5fd4c 100644
--- a/doc/user_guide/make.html
+++ b/doc/user_guide/make.html
@@ -41,7 +41,9 @@
   Make Configuration</a> for a full list of declarations in an FCM Make
   configuration file.</p>
 
-  <h2 id="concept">FCM Make: Concept</h2>
+  <h2 id="concept">FCM Make Concept</h2>
+
+  <h3 id="concept.cli">FCM Make Concept: Command Line Interface</h3>
 
   <p>The FCM make system can be invoked using the command line interface:</p>
   <pre>
@@ -74,6 +76,8 @@ fcm make [OPTIONS] [DECLARAION ...]
   <p>For details of the other command line options please see <a href=
   "command_ref.html#fcm-make">FCM Command Reference > fcm make</a>.</p>
 
+  <h3 id="concept.cfg">FCM Make Concept: Configuration File</h3>
+
   <p>The FCM make configuration file is expected to be an FCM configuration
   file. (See <a href="annex_cfg.html">Annex: FCM Configuration File</a>.) A
   typical FCM make configuration file may look like:</p>
@@ -123,52 +127,103 @@ build-that.target = that.exe
   define the configurations for <samp>build-this</samp> and
   <samp>build-that</samp> respectively.</p>
 
-  <dl>
-    <dt>Directory Structure</dt>
+  <h3 id="concept.use">FCM Make Concept: Inheritance</h3>
 
-    <dd>
-      <p>When you run <code>fcm make</code>, it will create a directory
-      structure that may look like:</p>
-      <pre>
+  <p>The FCM Make system allows inheritance of configuration and files from
+  succeeded makes, so the current make does not have to re-do everything that
+  may already be available else where. To do this, specify the inheritance with
+  a <code><a href= "annex_cfg.html#make.use">use</a> declaration</code>,
+  e.g.:</p>
+
+  <pre>
+use = /path/to/succeeded/make/
+</pre>
+
+  <p>For more information on how an inheritance behaves, see:</p>
+
+  <ul>
+    <li><a href="#extract.inherit">Extract Inheritance</a></li>
+
+    <li><a href="#build.inherit">Build Inheritance</a></li>
+  </ul>
+
+  <h3 id="concept.dest">FCM Make Concept: Directory Structure</h3>
+
+  <p>When you run <code>fcm make</code>, it will create a directory
+  structure that may look like:</p>
+
+  <pre>
 .fcm-make/...
 extract/...
 build/...
 ...
 </pre>
 
-      <p>Each normal sub-directory, such as <samp>extract/</samp> and
-      <samp>build/</samp>, contains the result of each step. The hidden
-      sub-directory <samp>.fcm-make/</samp> is used by <code>fcm make</code> as
-      a working area. It may contain the following items:</p>
-
-      <p><samp>.fcm-make/cache/</samp> An area for caching non-local items.
-      E.g. the extract system exports source trees from the version control
-      system into this cache.</p>
-
-      <p><samp>fcm-make-as-parsed.cfg ->
-      .fcm-make/config-as-parsed.cfg</samp> The configuration file as
-      parsed by the latest <code>fcm make</code> command at this
-      destination.</p>
-
-      <p><samp>fcm-make-on-success.cfg ->
-      .fcm-make/config-on-success.cfg</samp> The configuration file
-      that can be used to repeat the latest successful <code>fcm make</code>
-      command at this destination.</p>
-
-      <p><samp>.fcm-make/ctx.gz</samp> A serialised data structure that
-      represents the context of the latest <code>fcm make</code> command at
-      this destination. It is a <code>gzip</code> file containing data in the
-      <a href="http://perldoc.perl.org/Storable.html">Perl Storable</a>
-      format.</p>
-
-      <p><samp>fcm-make.log -> .fcm-make/log</samp>
-      A diagnostic log generated by the latest
-      <code>fcm make</code> command at this destination. The content should be
-      equivalent to the diagnostic output in STDOUT and STDERR at
-      <code>-vv</code> verbosity.</p>
-    </dd>
+  <p>Each normal sub-directory, such as <samp>extract/</samp> and
+  <samp>build/</samp>, contains the result of each step. The hidden
+  sub-directory <samp>.fcm-make/</samp> is used by <code>fcm make</code> as a
+  working area. It may contain the following items:</p>
+
+  <dl>
+    <dt><samp>.fcm-make/cache/</samp></dt>
+
+    <dd>An area for caching non-local items. E.g. the extract system exports
+    source trees from the version control system into this cache. If <code>fcm
+    make</code> is invoked with the <code>--archive</code> option, contents in
+    this directory will be compressed into TAR-GZIP files, e.g.
+    <samp>.fcm-make/cache/extract/</samp> will become
+    <samp>.fcm-make/cache/extract.tar.gz</samp>.</dd>
+
+    <dt><samp>fcm-make-as-parsed.cfg ->
+    .fcm-make/config-as-parsed.cfg</samp></dt>
+
+    <dd>The configuration file as parsed by the latest <code>fcm make</code>
+    command at this destination.</dd>
+
+    <dt><samp>fcm-make-on-success.cfg ->
+    .fcm-make/config-on-success.cfg</samp></dt>
+
+    <dd>The configuration file that can be used to repeat the latest successful
+    <code>fcm make</code> command at this destination.</dd>
+
+    <dt><samp>.fcm-make/ctx.gz</samp></dt>
+    
+    <dd>A serialised data structure that represents the context of the latest
+    <code>fcm make</code> command at this destination.  It is a
+    <code>gzip</code> file containing data in the <a
+    href="http://perldoc.perl.org/Storable.html">Perl Storable</a> format.</dd>
+
+    <dt><samp>fcm-make.log -> .fcm-make/log</samp></dt>
+    
+    <dd>A diagnostic log generated by the latest <code>fcm make</code> command
+    at this destination. The content should be equivalent to the diagnostic
+    output in STDOUT and STDERR at <code>-vv</code> verbosity.</dd>
   </dl>
 
+  <h3 id="concept.name">FCM Make Concept: Context Name</h3>
+
+  <p>You may sometimes need to run <code>fcm make</code> in the same location of
+  the file system. Perhaps you are on a network with a shared file system, but
+  only certain tools are available on different hosts, e.g. you can only extract
+  on one host and build on a different host, you should name the makes so that
+  they don't end up overwriting each other's context, logs and other
+  outputs. To do so, you can use the <code>--name=NAME</code> option on the
+  command line, and/or the <a href="annex_cfg.html#make.name">name</a>
+  declaration in the configuration file. Using <code>--name=2</code> as an
+  example, you will get the following:</p>
+
+  <ul>
+    <li>The command will search for <code>fcm-make2.cfg</code> instead of
+    <code>fcm-make.cfg</code>.</li>
+
+    <li>The command will dump context, logs, etc with file names such as
+    <samp>.fcm-make2/*</samp>, <samp>fcm-make2-as-parsed.cfg</samp>,
+    <samp>fcm-make2.log</samp>, etc.</li>
+
+    <li>The command will only allow inheritance from a location where a
+    successful make with the same name exists.</li>
+  </ul>
+
   <h2 id="extract">Extract</h2>
 
   <p>The extract system provides an interface between the version control
@@ -744,7 +799,8 @@ extract/src/egg/scrambled.bash
 steps = extract mirror                            # 1
 # ... some extract declarations
 mirror.target = user at somewhere:/path/in/somewhere # 2
-mirror.prop{config-file.steps} = preprocess build # 3
+mirror.prop{config-file.name} = -at-somewhere     # 3
+mirror.prop{config-file.steps} = preprocess build # 4
 # ... some preprocess declarations
 # ... some build declarations
 </pre>
@@ -752,12 +808,17 @@ mirror.prop{config-file.steps} = preprocess build # 3
   <p>When the system runs with this configuration, the system will mirror the
   result of the extract to the <a href=
   "annex_cfg.html#make.mirror.target">mirror.target</a>, i.e.
-  <samp>user at somewhere:/path/in/somewhere</samp> using <code>ssh</code> and
-  <code>rsync</code>. With the <a href=
+  <samp>somewhere:/path/in/somewhere</samp> using <code>ssh</code> and
+  <code>rsync</code>.</p>
+  
+  <p>With the <a href=
+  "annex_cfg.html#make.mirror.prop.config-file.name">config-file.name</a>
+  property set at point 3 and the <a href=
   "annex_cfg.html#make.mirror.prop.config-file.steps">config-file.steps</a>
-  property set at point 3, it will write a <samp>fcm-make.cfg</samp> in the
-  mirror target so that the <samp>preprocess</samp> and <samp>build</samp>
-  steps can continue there.</p>
+  property set at point 4, it will write a configuration file called
+  <samp>fcm-make-at-somewhere.cfg</samp> with the make name set as
+  <samp>-at-somewhere</samp> in the mirror target so that the
+  <samp>preprocess</samp> and <samp>build</samp> steps can continue there.</p>
 
   <h3 id="mirror.diagnostic">Mirror Diagnostic</h3>
 
@@ -883,6 +944,14 @@ build/o/...
   <p>Sub-directories are only created as necessary, so you may not find all of
   the above in your destination tree.</p>
 
+  <p>If <code>fcm make</code> is invoked with the <code>--archive</code> option,
+  sub-directories in categories containing intermediate build files (or any
+  category specified in the <a href=
+  "#make.build.prop.archive-ok-target-category">archive-ok-target-category</a>
+  property) will be put into TAR-GZIP files. E.g. with the default setting,
+  <samp>include/</samp> and <samp>o/</samp> will become
+  <samp>include.tar.gz</samp> and <samp>o.tar.gz</samp> respectively.</p>
+
   <p>To use a different compiler and/or compiler options for Fortran/C/C++, you
   use the <a href="annex_cfg.html#make.build.prop">build.prop</a> declaration to
   redefine the build properties. E.g.:</p>
@@ -2284,7 +2353,7 @@ preprocess.target{ns} =
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/overview.html b/doc/user_guide/overview.html
index 8f20123..9d9c1bc 100644
--- a/doc/user_guide/overview.html
+++ b/doc/user_guide/overview.html
@@ -137,7 +137,7 @@
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/system_admin.html b/doc/user_guide/system_admin.html
index 86b2c99..07cbf24 100644
--- a/doc/user_guide/system_admin.html
+++ b/doc/user_guide/system_admin.html
@@ -594,7 +594,7 @@ EOF
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/doc/user_guide/working_practices.html b/doc/user_guide/working_practices.html
index a6a4204..c13553f 100644
--- a/doc/user_guide/working_practices.html
+++ b/doc/user_guide/working_practices.html
@@ -804,7 +804,7 @@ M      document.doc
   <div class="container-fluid text-center">
     <div class="row-fluid"><div class="span12">
     <address><small>
-      © British Crown Copyright 2006-14
+      © British Crown Copyright 2006-15
       <a href="http://www.metoffice.gov.uk">Met Office</a>.
       See <a href="../etc/fcm-terms-of-use.html">Terms of Use</a>.<br />
       This document is released under the British <a href=
diff --git a/etc/svn-hooks/post-commit b/etc/svn-hooks/post-commit
index e486c64..2188421 100755
--- a/etc/svn-hooks/post-commit
+++ b/etc/svn-hooks/post-commit
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/etc/svn-hooks/post-revprop-change b/etc/svn-hooks/post-revprop-change
index 8240fb2..4b77643 100755
--- a/etc/svn-hooks/post-revprop-change
+++ b/etc/svn-hooks/post-revprop-change
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/etc/svn-hooks/pre-commit b/etc/svn-hooks/pre-commit
index 8c618da..6a3783c 100755
--- a/etc/svn-hooks/pre-commit
+++ b/etc/svn-hooks/pre-commit
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/etc/svn-hooks/pre-revprop-change b/etc/svn-hooks/pre-revprop-change
index fa0338a..7cd8226 100755
--- a/etc/svn-hooks/pre-revprop-change
+++ b/etc/svn-hooks/pre-revprop-change
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Admin/Config.pm b/lib/FCM/Admin/Config.pm
index caa1358..5b1186c 100644
--- a/lib/FCM/Admin/Config.pm
+++ b/lib/FCM/Admin/Config.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Admin/Project.pm b/lib/FCM/Admin/Project.pm
index 45490b5..a02f5ef 100644
--- a/lib/FCM/Admin/Project.pm
+++ b/lib/FCM/Admin/Project.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Admin/Runner.pm b/lib/FCM/Admin/Runner.pm
index ee9a1e5..320ce0d 100644
--- a/lib/FCM/Admin/Runner.pm
+++ b/lib/FCM/Admin/Runner.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Admin/System.pm b/lib/FCM/Admin/System.pm
index 2c87cea..ec353d4 100644
--- a/lib/FCM/Admin/System.pm
+++ b/lib/FCM/Admin/System.pm
@@ -1,5 +1,5 @@
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -193,14 +193,6 @@ sub add_trac_environment {
         "adding TICKET_EDIT_DESCRIPTION permission to authenticated",
         qw{permission add}, 'authenticated', qw{TICKET_EDIT_DESCRIPTION},
     );
-    eval {$TRAC_ADMIN->(
-        "adding TICKET_EDIT_COMMENT permission to authenticated",
-        qw{permission add}, 'authenticated', qw{TICKET_EDIT_COMMENT},
-    )};
-    if ($@) {
-        # Expected to fail for Trac < 0.12
-        $@ = undef;
-    }
     $RUN->(
         "adding names and emails of users",
         sub {manage_users_in_trac_db_of($project, {get_users()})},
@@ -1132,7 +1124,7 @@ sub _manage_users_in_trac_db_of {
     SESSION_ATTRIBUTE: {
         my $attribute_select_statement = $db_handle->prepare(
             "SELECT sid,name,value FROM session_attribute "
-                . "WHERE authenticated == 1 AND (name == ? OR name == ?)",
+                . "WHERE authenticated == 1",
         );
         my $attribute_insert_statement = $db_handle->prepare(
             "INSERT INTO session_attribute VALUES (?, 1, ?, ?)",
@@ -1144,14 +1136,17 @@ sub _manage_users_in_trac_db_of {
         my $attribute_delete_statement = $db_handle->prepare(
             "DELETE FROM session_attribute WHERE sid == ?",
         );
-        $attribute_select_statement->execute('name', 'email');
+        my $attribute_delete_name_statement = $db_handle->prepare(
+            "DELETE FROM session_attribute WHERE sid == ? AND name == ?",
+        );
+        $attribute_select_statement->execute();
         my %attribute_old_users;
+        my %deleted_users;
         ROW:
         while (my @row = $attribute_select_statement->fetchrow_array()) {
             my ($sid, $name, $value) = @row;
             my $user = exists($user_ref->{$sid})? $user_ref->{$sid} : undef;
             if (defined($user)) {
-                $attribute_old_users{$sid} = 1;
                 my $getter
                     = $name eq 'name'  ? 'get_display_name'
                     : $name eq 'email' ? 'get_email'
@@ -1159,8 +1154,9 @@ sub _manage_users_in_trac_db_of {
                 if (!defined($getter)) {
                     next ROW;
                 }
-                if ($user->$getter() ne $value) {
-                    my $new_value = $user->$getter();
+                $attribute_old_users{"$sid|$name"} = 1;
+                my $new_value = $user->$getter();
+                if ($new_value && $new_value ne $value) {
                     $RUNNER->run(
                         "session_attribute: updating $name: $sid: $new_value",
                         sub {return $attribute_update_statement->execute(
@@ -1168,34 +1164,43 @@ sub _manage_users_in_trac_db_of {
                         )},
                     );
                 }
+                elsif (!$new_value && $value) {
+                    $RUNNER->run(
+                        "session_attribute: removing $name: $sid",
+                        sub {return $attribute_delete_name_statement->execute(
+                            $sid, $name,
+                        )},
+                    );
+                }
             }
-            else {
+            elsif (!exists($deleted_users{$sid})) {
+                $deleted_users{$sid} = 1;
                 $RUNNER->run(
                     "session_attribute: removing $sid",
                     sub {return $attribute_delete_statement->execute($sid)},
                 );
             }
         }
-        USER:
         for my $sid (keys(%{$user_ref})) {
-            if (exists($attribute_old_users{$sid})) {
-                next USER;
-            }
             my $user = $user_ref->{$sid};
-            my $display_name = $user->get_display_name();
-            my $email        = $user->get_email();
-            $RUNNER->run(
-                "session_attribute: adding name: $sid: $display_name",
-                sub {return $attribute_insert_statement->execute(
-                    $sid, 'name', $display_name,
-                )},
-            );
-            $RUNNER->run(
-                "session_attribute: adding email: $sid: $email",
-                sub {return $attribute_insert_statement->execute(
-                    $sid, 'email', $email,
-                )},
-            );
+            ATTRIB:
+            for (
+                ['name' , $user->get_display_name()],
+                ['email', $user->get_email()       ],
+            ) {
+                my ($name, $value) = @{$_};
+                if (exists($attribute_old_users{"$sid|$name"})) {
+                    next ATTRIB;
+                }
+                if ($value) {
+                    $RUNNER->run(
+                        "session_attribute: adding $name: $sid: $value",
+                        sub {$attribute_insert_statement->execute(
+                            $sid, $name, $value,
+                        )},
+                    );
+                }
+            }
         }
         $attribute_select_statement->finish();
         $attribute_insert_statement->finish();
diff --git a/lib/FCM/Admin/User.pm b/lib/FCM/Admin/User.pm
index 2db3303..27b337d 100644
--- a/lib/FCM/Admin/User.pm
+++ b/lib/FCM/Admin/User.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Admin/Users/LDAP.pm b/lib/FCM/Admin/Users/LDAP.pm
index a08ad17..fdd5047 100644
--- a/lib/FCM/Admin/Users/LDAP.pm
+++ b/lib/FCM/Admin/Users/LDAP.pm
@@ -1,6 +1,6 @@
 
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Admin/Users/Passwd.pm b/lib/FCM/Admin/Users/Passwd.pm
index 769f799..259f957 100644
--- a/lib/FCM/Admin/Users/Passwd.pm
+++ b/lib/FCM/Admin/Users/Passwd.pm
@@ -1,5 +1,5 @@
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -43,10 +43,6 @@ sub _get_users_info {
     if (@only_users) {
         return _get_only_users_info($attrib_ref, @only_users);
     }
-    my $domain = $CONFIG->get_passwd_email_domain() || q{};
-    if ($domain) {
-        $domain = '@' . $domain;
-    }
     my $gid_max = $CONFIG->get_passwd_gid_max();
     my $uid_max = $CONFIG->get_passwd_uid_max();
     my $gid_min = $CONFIG->get_passwd_gid_min();
@@ -62,10 +58,14 @@ sub _get_users_info {
         ) {
             next USER;
         }
+        my $email = _guess_email_from_gecos($attrib_ref, $gecos);
+        if (!$email) {
+            next USER;
+        }
         $user_of{$name} = FCM::Admin::User->new({
             name         => $name,
-            display_name => $gecos,
-            email        => $gecos . $domain,
+            display_name => (split(q{,}, $gecos))[0],
+            email        => $email,
         });
     }
     endpwent();
@@ -76,25 +76,29 @@ sub _get_users_info {
 # %user_of = ($name => <FCM::Admin::User instance>, ...)
 sub _get_only_users_info {
     my ($attrib_ref, @only_users) = @_;
-    my $domain = $CONFIG->get_passwd_email_domain() || q{};
-    if ($domain) {
-        $domain = '@' . $domain;
-    }
-    my @ok_uids = shellwords($CONFIG->get_passwd_ok_uids());
     my %user_of;
     for my $user (@only_users) {
         my ($name, $gecos) = (getpwnam($user))[0, 6];
-        if ($name && $gecos && $gecos =~ qr{\A[\w\.\-]+\.[\w\.\-]+\z}msx) {
+        if ($name && $gecos) {
             $user_of{$name} = FCM::Admin::User->new({
                 name         => $name,
-                display_name => $gecos,
-                email        => $gecos . $domain,
+                display_name => (split(q{,}, $gecos))[0],
+                email        => _guess_email_from_gecos($attrib_ref, $gecos),
             });
         }
     }
     return (wantarray() ? %user_of : \%user_of);
 }
 
+# Guess a user's email from gecos information
+sub _guess_email_from_gecos {
+    my ($attrib_ref, $gecos) = @_;
+    my $domain = $CONFIG->get_passwd_email_domain();
+    my $name = index($gecos, q{,}) > 0 ? (split(q{,}, $gecos))[0] : $gecos;
+    return ($name =~ qr{\s}msx)
+        ? undef : lc($name) . ($domain ? '@' . $domain : q{});
+}
+
 # Return a list of bad users in @users.
 sub _verify_users {
     my ($attrib_ref, @users) = @_;
diff --git a/lib/FCM/Admin/Util.pm b/lib/FCM/Admin/Util.pm
index 524339d..d9962f5 100644
--- a/lib/FCM/Admin/Util.pm
+++ b/lib/FCM/Admin/Util.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -118,12 +118,11 @@ sub run_create_archive {
     FCM::Admin::Runner->instance()->run(
         "creating archive $archive_path",
         sub {
-            return !system(
-                qw{tar -c -z},
-                q{-C} => $work_dir,
-                q{-f} => $archive_path,
-                @base_names,
-            );
+            my $command
+                = qq{tar -c -z -C '$work_dir' -f -}
+                . q{ } . join(q{ }, map {qq{'$_'}} @base_names)
+                . qq{ | dd 'conv=fsync' 'of=$archive_path'};
+            return !system($command);
             # Note: can use Archive::Tar, but "tar" is much faster.
         },
     );
diff --git a/lib/FCM/CLI.pm b/lib/FCM/CLI.pm
index c4fd6fd..17dd311 100644
--- a/lib/FCM/CLI.pm
+++ b/lib/FCM/CLI.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/CLI/Exception.pm b/lib/FCM/CLI/Exception.pm
index 85631ef..06f5956 100644
--- a/lib/FCM/CLI/Exception.pm
+++ b/lib/FCM/CLI/Exception.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/CLI/Parser.pm b/lib/FCM/CLI/Parser.pm
index a85875a..afab456 100644
--- a/lib/FCM/CLI/Parser.pm
+++ b/lib/FCM/CLI/Parser.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -66,7 +66,7 @@ our %OPTION_OF = map {
     [['jobs'               ,            ], ['j'], OPT_SCAL],
     [['list'               ,            ], ['l'], OPT_BOOL],
     [['name'               ,            ], ['n'], OPT_SCAL],
-    [['new'                ,            ], ['n'], OPT_BOOL],
+    [['new'                ,            ], ['N'], OPT_BOOL],
     [['non-interactive'    ,            ], [   ], OPT_BOOL],
     [['only'               ,            ], [   ], OPT_LIST],
     [['organisation'       ,            ], [   ], OPT_SCAL],
@@ -158,15 +158,16 @@ our %OPTIONS_FOR = (
     $HELP_APP       => [@OPTION_OF{qw{quiet verbose}}],
     'keyword-print' => [@OPTION_OF{qw{verbose}}],
     'loc-layout'    => [@OPTION_OF{qw{verbose}}],
-    'merge'         => [@OPTION_OF{
-        qw{auto-log custom dry-run non-interactive quiet reverse revision verbose}
-    }],
-    'mkpatch'       => [@OPTION_OF{qw{exclude organisation revision}}],
     'make'          => [@OPTION_OF{
-        qw{ directory ignore-lock jobs config-file config-file-path new quiet
-            verbose
+        qw{ archive directory ignore-lock jobs config-file config-file-path name
+            new quiet verbose
         }
     }],
+    'merge'         => [@OPTION_OF{
+        qw{ auto-log custom dry-run non-interactive quiet reverse revision
+            verbose}
+    }],
+    'mkpatch'       => [@OPTION_OF{qw{exclude organisation revision}}],
     'project-create'=> [@OPTION_OF{
         qw{non-interactive password svn-non-interactive}
     }],
diff --git a/lib/FCM/CLI/fcm-export-items.pod b/lib/FCM/CLI/fcm-export-items.pod
index 0a3ffda..da75289 100644
--- a/lib/FCM/CLI/fcm-export-items.pod
+++ b/lib/FCM/CLI/fcm-export-items.pod
@@ -29,7 +29,7 @@ Specify the path to the configuration file.
 
 Specify the path to the destination. (default=$PWD)
 
-=item --new
+=item --new, -N
 
 Specify the new mode. In this mode, everything is re-exported. Otherwise, the
 system runs in incremental mode, in which the version directories are only
diff --git a/lib/FCM/CLI/fcm-make.pod b/lib/FCM/CLI/fcm-make.pod
index fbf6a48..be1ea00 100644
--- a/lib/FCM/CLI/fcm-make.pod
+++ b/lib/FCM/CLI/fcm-make.pod
@@ -17,6 +17,16 @@ configuration file.
 
 =over 4
 
+=item --archive, -a
+
+Switch on archive mode. In archive mode, intermediate files will be put into
+TAR-GZIP archives on completion, e.g. extract system:
+C<.fcm-make/cache/extract/>, and build system: C<build/include/> and
+C<build/o/>.
+
+The archive mode is not suitable for a make that will be inherited or used by
+other makes.
+
 =item --config-file-path=PATH, -F PATH
 
 Specify paths for searching configuration files specified in relative paths.
@@ -28,8 +38,7 @@ current working directory)
 
 =item --directory=PATH, -C PATH
 
-Specify the path to the destination. (default = $PWD or whatever is specified
-in the "dest" setting in the configuration file)
+Change directory to C<PATH> before doing anything. (default = $PWD)
 
 =item --ignore-lock
 
@@ -42,7 +51,13 @@ will fail. This option can be used to bypass this check.
 
 Specify the number of (child) processes that can be run simultaneously.
 
-=item --new
+=item --name=NAME, -n NAME
+
+Specify a name for the make, so that the command will search for
+fcm-makeC<NAME>.cfg instead of fcm-make.cfg, and will write context files in
+.fcm-makeC<NAME>/ and log files as fcm-makeC<NAME>.log, etc.
+
+=item --new, -N
 
 Remove items in the destination created by the previous make, and starts a new
 make.
diff --git a/lib/FCM/CLI/fcm-merge.pod b/lib/FCM/CLI/fcm-merge.pod
index d49cc58..19c251d 100644
--- a/lib/FCM/CLI/fcm-merge.pod
+++ b/lib/FCM/CLI/fcm-merge.pod
@@ -37,10 +37,12 @@ command will peg the URL with its last changed revision.
 =item 3.
 
 If --reverse is specified, the command performs a reverse merge of the
-changeset(s) specified by the --revision option. If a single revision is
-specified, the merge delta is N:(N - 1). Otherwise, the merge delta is M:N,
-where M > N. Note that you do not have to specify a SOURCE for a reverse merge,
-because the SOURCE should always be the branch your working copy is pointing to.
+changeset(s) specified by the --revision=M:N option. If a revision is not
+specified with --rev=M:N, it attempts to merge the delta COMMITTED:(COMMITTED -
+1). If a single revision N is specified, the merge delta is N:(N - 1).
+Otherwise, the merge delta is M:N, where M > N. Note that you do not have to
+specify a SOURCE for a reverse merge, because the SOURCE should always be the
+branch your working copy is pointing to.
   
 =back
 
diff --git a/lib/FCM/Class/CODE.pm b/lib/FCM/Class/CODE.pm
index fda31dd..ebe5c55 100644
--- a/lib/FCM/Class/CODE.pm
+++ b/lib/FCM/Class/CODE.pm
@@ -1,5 +1,5 @@
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Class/Exception.pm b/lib/FCM/Class/Exception.pm
index 0f54896..fbd1f86 100644
--- a/lib/FCM/Class/Exception.pm
+++ b/lib/FCM/Class/Exception.pm
@@ -1,5 +1,5 @@
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Class/HASH.pm b/lib/FCM/Class/HASH.pm
index 97cd37f..2c4496a 100644
--- a/lib/FCM/Class/HASH.pm
+++ b/lib/FCM/Class/HASH.pm
@@ -1,5 +1,5 @@
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Context/ConfigEntry.pm b/lib/FCM/Context/ConfigEntry.pm
index 090b82a..62d77d4 100644
--- a/lib/FCM/Context/ConfigEntry.pm
+++ b/lib/FCM/Context/ConfigEntry.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Context/Event.pm b/lib/FCM/Context/Event.pm
index 5e6a090..31ef55c 100644
--- a/lib/FCM/Context/Event.pm
+++ b/lib/FCM/Context/Event.pm
@@ -1,5 +1,5 @@
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Context/Keyword.pm b/lib/FCM/Context/Keyword.pm
index af1fcda..ea61d5b 100644
--- a/lib/FCM/Context/Keyword.pm
+++ b/lib/FCM/Context/Keyword.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Context/Locator.pm b/lib/FCM/Context/Locator.pm
index 5959aac..5ade4ef 100644
--- a/lib/FCM/Context/Locator.pm
+++ b/lib/FCM/Context/Locator.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Context/Make.pm b/lib/FCM/Context/Make.pm
index 4551144..523bc27 100644
--- a/lib/FCM/Context/Make.pm
+++ b/lib/FCM/Context/Make.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -36,6 +36,7 @@ __PACKAGE__->class({
     dest_lock         => '$',
     error             => {},
     inherit_ctx_list  => '@',
+    name              => {isa => '$', default => q{}},
     option_of         => '%',
     prev_ctx          => __PACKAGE__,
     status            => {isa => '$', default => ST_UNKNOWN},
@@ -89,6 +90,12 @@ This should be set to the value of the exception, if this make ends in one.
 
 An ARRAY of contexts inherited by this make.
 
+=item name
+
+The name of the context. This is useful if we need to have multiple (but
+non-overlapping) "fcm make" runs in the same destination. (Default is a null
+string.)
+
 =item option_of
 
 A HASH to store the options of this make. See L</OPTION> for detail.
diff --git a/lib/FCM/Context/Make/Build.pm b/lib/FCM/Context/Make/Build.pm
index 8489963..d035a74 100644
--- a/lib/FCM/Context/Make/Build.pm
+++ b/lib/FCM/Context/Make/Build.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Context/Make/Extract.pm b/lib/FCM/Context/Make/Extract.pm
index 8e81b39..133df3c 100644
--- a/lib/FCM/Context/Make/Extract.pm
+++ b/lib/FCM/Context/Make/Extract.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Context/Make/Mirror.pm b/lib/FCM/Context/Make/Mirror.pm
index 3f6110b..a722db7 100644
--- a/lib/FCM/Context/Make/Mirror.pm
+++ b/lib/FCM/Context/Make/Mirror.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Context/Make/Share/Property.pm b/lib/FCM/Context/Make/Share/Property.pm
index cc81196..d5904ae 100644
--- a/lib/FCM/Context/Make/Share/Property.pm
+++ b/lib/FCM/Context/Make/Share/Property.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Context/Task.pm b/lib/FCM/Context/Task.pm
index d49fe6c..cb80349 100644
--- a/lib/FCM/Context/Task.pm
+++ b/lib/FCM/Context/Task.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Exception.pm b/lib/FCM/Exception.pm
index edd45c2..c9417b7 100644
--- a/lib/FCM/Exception.pm
+++ b/lib/FCM/Exception.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System.pm b/lib/FCM/System.pm
index 5d06d0e..9218cdc 100644
--- a/lib/FCM/System.pm
+++ b/lib/FCM/System.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/CM.pm b/lib/FCM/System/CM.pm
index 51aba6a..0a09438 100644
--- a/lib/FCM/System/CM.pm
+++ b/lib/FCM/System/CM.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -300,8 +300,10 @@ sub _cm_branch_create {
 sub _cm_branch_list {
     my ($attrib_ref, $option_ref, @args) = @_;
     _parse_args($attrib_ref, $option_ref, \@args);
+    my $used_default_arg;
     if (!@args) {
         @args = cwd() . '@HEAD';
+        $used_default_arg = 1;
     }
     my %common_patterns_at;
     if ($option_ref->{'only'} && @{$option_ref->{'only'}}) {
@@ -317,6 +319,10 @@ sub _cm_branch_list {
         my %patterns_at = %{dclone(\%common_patterns_at)};
         my %info = eval {%{$attrib_ref->{svn}->get_info($arg)->[0]}};
         if ($@) {
+            if ($used_default_arg) {
+                # Can't complain about a bad arg if we put it there.
+                return $E->throw($E->SHELL, $@->{ctx}, $@->{ctx}->{e});
+            }
             return $E->throw($E->CM_ARG, $arg);
         }
         my $url = $info{'url'} . '@' . $info{'revision'};
diff --git a/lib/FCM/System/CM/CommitMessage.pm b/lib/FCM/System/CM/CommitMessage.pm
index a09fbb4..2e8da61 100644
--- a/lib/FCM/System/CM/CommitMessage.pm
+++ b/lib/FCM/System/CM/CommitMessage.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/CM/Prompt.pm b/lib/FCM/System/CM/Prompt.pm
index 1217c4f..e529872 100644
--- a/lib/FCM/System/CM/Prompt.pm
+++ b/lib/FCM/System/CM/Prompt.pm
@@ -1,5 +1,5 @@
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/CM/ResolveConflicts.pm b/lib/FCM/System/CM/ResolveConflicts.pm
index da9e96a..636d00f 100644
--- a/lib/FCM/System/CM/ResolveConflicts.pm
+++ b/lib/FCM/System/CM/ResolveConflicts.pm
@@ -1,5 +1,5 @@
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/CM/SVN.pm b/lib/FCM/System/CM/SVN.pm
index 8e84e8f..aa9cc0b 100644
--- a/lib/FCM/System/CM/SVN.pm
+++ b/lib/FCM/System/CM/SVN.pm
@@ -1,5 +1,5 @@
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -45,6 +45,7 @@ our %LAYOUT_CONFIG = (
     'dir-tag' => 'tags',
     'level-owner-branch' => 2,
     'level-owner-tag' => undef,
+    'owner' => undef,
     'template-branch' => '{category}/{owner}/{name_prefix}{name}',
     'template-tag' => undef,
 );
@@ -259,7 +260,7 @@ sub _get_layout_common {
         }
         if (!defined($project)) {
             # $path does not contain the trunk sub-directory, need to search
-            # for it 
+            # for it
             my @head = ();
             my @tail = @names;
             while (@head <= @names) {
@@ -622,7 +623,8 @@ sub _stdout {
     if ($value_of{rc}) {
         return $E->throw(
             $E->SHELL,
-            {command_list => \@command, %value_of}
+            {command_list => \@command, %value_of},
+            $value_of{e}
         );
     }
     wantarray() ? split("\n", $value_of{o}) : $value_of{o};
diff --git a/lib/FCM/System/Exception.pm b/lib/FCM/System/Exception.pm
index b7a356e..94c1d7a 100644
--- a/lib/FCM/System/Exception.pm
+++ b/lib/FCM/System/Exception.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make.pm b/lib/FCM/System/Make.pm
index 3e13021..b367772 100644
--- a/lib/FCM/System/Make.pm
+++ b/lib/FCM/System/Make.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -31,9 +31,10 @@ use FCM::System::Make::Mirror;
 use FCM::System::Make::Preprocess;
 use FCM::System::Make::Share::Config;
 use FCM::System::Make::Share::Dest;
+use File::Basename qw{basename};
+use File::Copy qw{copy};
 use File::Path qw{rmtree};
 use File::Spec::Functions qw{catfile};
-use File::Copy qw{copy};
 use File::Temp;
 use POSIX qw{strftime};
 use Sys::Hostname qw{hostname};
@@ -132,37 +133,33 @@ sub _config_parse {
 # Sets up the destination.
 sub _dest_init {
     my ($attrib_ref, $m_ctx) = @_;
-    $attrib_ref->{shared_util_of}{dest}->dest_init($m_ctx);
+    my $DEST_UTIL = $attrib_ref->{shared_util_of}{dest};
+    $DEST_UTIL->dest_init($m_ctx);
 
     # Move temporary log file to destination
     my $now = strftime("%Y%m%dT%H%M%S", gmtime());
-    my $log = $attrib_ref->{shared_util_of}{dest}->path($m_ctx, 'sys-log');
+    my $log = $DEST_UTIL->path($m_ctx, 'sys-log');
     my $log_actual = sprintf("%s-%s", $log, $now);
-    _symlink($log_actual, $log);
+    _symlink(basename($log_actual), $log);
     (       close($attrib_ref->{handle_log})
         &&  copy($attrib_ref->{handle_log}->filename(), $log)
         &&  open(my $handle_log, '>>', $log)
     ) || return $E->throw($E->DEST_CREATE, $log, $!);
     _symlink(
-        $FCM::System::Make::Share::Dest::PATH_OF{'sys-log'},
-        $attrib_ref->{shared_util_of}{dest}->path($m_ctx, 'sys-log-symlink'),
+        $DEST_UTIL->path({'name' => $m_ctx->get_name()}, 'sys-log'),
+        $DEST_UTIL->path($m_ctx, 'sys-log-symlink'),
     );
     my $log_ctx = $attrib_ref->{util}->util_of_report()->get_ctx($m_ctx);
     $log_ctx->set_handle($handle_log);
 
     # Saves as parsed config
-    my $cfg = $attrib_ref->{shared_util_of}{dest}->path(
-        $m_ctx, 'sys-config-as-parsed',
-    );
+    my $cfg = $DEST_UTIL->path($m_ctx, 'sys-config-as-parsed');
     (       close($attrib_ref->{handle_cfg})
         &&  copy($attrib_ref->{handle_cfg}->filename(), $cfg)
     ) || return $E->throw($E->DEST_CREATE, $cfg, $!);
     _symlink(
-        $FCM::System::Make::Share::Dest::PATH_OF{'sys-config-as-parsed'},
-        $attrib_ref->{shared_util_of}{dest}->path(
-            $m_ctx,
-            'sys-config-as-parsed-symlink',
-        ),
+        $DEST_UTIL->path({'name' => $m_ctx->get_name()}, 'sys-config-as-parsed'),
+        $DEST_UTIL->path($m_ctx, 'sys-config-as-parsed-symlink'),
     );
 }
 
@@ -180,7 +177,11 @@ sub _main {
     }
     # Starts the system
     my $m_ctx = FCM::Context::Make->new({option_of => $option_hash_ref});
-    my $T = sub {_timer_wrap($attrib_ref, @_)};
+    if ($m_ctx->get_option_of('name')) {
+        $m_ctx->set_name($m_ctx->get_option_of('name'));
+    }
+    my $T = sub {_timer_wrap($attrib_ref, $m_ctx, @_)};
+    my $DEST_UTIL = $attrib_ref->{shared_util_of}{dest};
     eval {$T->(
         sub {
             my %attrib = (
@@ -223,9 +224,7 @@ sub _main {
                 $ctx->set_status($m_ctx->ST_INIT);
                 if ($ctx->can('set_dest')) {
                     $ctx->set_dest(
-                        $attrib_ref->{shared_util_of}{dest}->path(
-                            $m_ctx, 'target', $ctx->get_id(),
-                        ),
+                        $DEST_UTIL->path($m_ctx, 'target', $ctx->get_id()),
                     );
                 }
                 eval {$T->(sub {$impl->main($m_ctx, $ctx)}, $step)};
@@ -250,17 +249,14 @@ sub _main {
         die("\n");
     }
     $m_ctx->set_status($m_ctx->ST_OK);
-    $attrib_ref->{shared_util_of}{dest}->save(
+    $DEST_UTIL->save(
         [$attrib_ref->{shared_util_of}{config}->unparse($m_ctx)],
         $m_ctx,
         'sys-config-on-success',
     );
     _symlink(
-        $FCM::System::Make::Share::Dest::PATH_OF{'sys-config-on-success'},
-        $attrib_ref->{shared_util_of}{dest}->path(
-            $m_ctx,
-            'sys-config-on-success-symlink',
-        ),
+        $DEST_UTIL->path({'name' => $m_ctx->get_name()}, 'sys-config-on-success'),
+        $DEST_UTIL->path($m_ctx, 'sys-config-on-success-symlink'),
     );
     _main_finally($attrib_ref, $m_ctx);
     return $m_ctx;
@@ -290,10 +286,15 @@ sub _symlink {
 
 # Wraps a piece of code with timer events.
 sub _timer_wrap {
-    my ($attrib_ref, $code_ref, @names) = @_;
+    my ($attrib_ref, $m_ctx, $code_ref, @names) = @_;
     my @event_args = (
         FCM::Context::Event->TIMER,
-        join(q{ }, $attrib_ref->{name}, @names),
+        join(
+            q{ },
+            $attrib_ref->{name},
+            ($m_ctx->get_name() ? $m_ctx->get_name() : ()),
+            @names,
+        ),
         time(),
     );
     $attrib_ref->{util}->event(@event_args);
diff --git a/lib/FCM/System/Make/Build.pm b/lib/FCM/System/Make/Build.pm
index 8e55c03..cbff538 100644
--- a/lib/FCM/System/Make/Build.pm
+++ b/lib/FCM/System/Make/Build.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -36,9 +36,9 @@ use FCM::System::Make::Build::FileType::H;
 use FCM::System::Make::Build::FileType::NS;
 use FCM::System::Make::Build::FileType::Script;
 use FCM::System::Make::Share::Subsystem;
-use File::Basename qw{basename dirname};
+use File::Basename qw{basename dirname fileparse};
 use File::Find qw{find};
-use File::Path qw{mkpath};
+use File::Path qw{mkpath rmtree};
 use File::Spec::Functions qw{abs2rel catfile rel2abs splitdir splitpath};
 use Storable qw{dclone};
 use Text::ParseWords qw{shellwords};
@@ -74,6 +74,7 @@ our %CONFIG_PARSER_OF = (
 # Default properties
 our %PROP_OF = (
     #                               [default       , ns-ok]
+    'archive-ok-target-category' => [q{include o}  , undef],
     'ignore-missing-dep-ns'      => [q{}           , undef],
     'no-step-source'             => [q{}           , undef],
     'no-inherit-source'          => [q{}           , undef],
@@ -97,6 +98,7 @@ __PACKAGE__->class(
             config_unparse            => \&_config_unparse,
             config_unparse_class_prop => \&_config_unparse_class_prop,
             ctx                       => \&_ctx,
+            ctx_load_hook             => \&_ctx_load_hook,
             main                      => \&_main,
         },
     },
@@ -304,6 +306,45 @@ sub _ctx {
     });
 }
 
+# Hook when loading a previous ctx.
+sub _ctx_load_hook {
+    my ($attrib_ref, $old_m_ctx, $old_ctx, $old_m_dest, $old_dest) = @_;
+    my $path_mod_func = sub {
+        my ($get_func, $set_func) = @_;
+        my $path = $get_func->();
+        if (!defined($path)) {
+            return;
+        }
+        my $rel_path = abs2rel($path, $old_m_dest);
+        if (index($rel_path, '..') != 0) {
+            $set_func->(catfile($old_m_ctx->get_dest(), $rel_path));
+        }
+    };
+    if (@{$old_ctx->get_dests()}) {
+        $old_ctx->get_dests()->[0] = $old_ctx->get_dest();
+    }
+    while (my ($ns, $source) = each(%{$old_ctx->get_source_of()})) {
+        $path_mod_func->(
+            sub {$source->get_path()},
+            sub {$source->set_path(@_)},
+        );
+    }
+    while (my ($key, $target) = each(%{$old_ctx->get_target_of()})) {
+        $path_mod_func->(
+            sub {$target->get_path()},
+            sub {$target->set_path(@_)},
+        );
+        $path_mod_func->(
+            sub {$target->get_path_of_prev()},
+            sub {$target->set_path_of_prev(@_)},
+        );
+        $path_mod_func->(
+            sub {$target->get_path_of_source()},
+            sub {$target->set_path_of_source(@_)},
+        );
+    }
+}
+
 # The main function of the class.
 sub _main {
     my ($attrib_ref, $m_ctx, $ctx) = @_;
@@ -404,13 +445,14 @@ sub _sources_locate_by_find {
             if (-d $path_found) {
                 return;
             }
-            my ($vol, $dir_name, $base) = splitpath($path_found);
-            for my $name (splitdir($dir_name), $base) {
-                if (index($name, q{.}) == 0) {
-                    return; # ignore Unix hidden/system files
+            my $ns = abs2rel($path_found, $path);
+            if ($ns ne q{.}) {
+                for my $name (split(q{/}, $ns)) {
+                    if (index($name, q{.}) == 0) {
+                        return; # ignore Unix hidden/system files
+                    }
                 }
             }
-            my $ns = abs2rel($path_found, $path);
             if ($key) {
                 $ns = $UTIL->ns_cat($key, $ns);
             }
@@ -615,6 +657,17 @@ sub _targets_update {
     }
     my $old_cwd = cwd();
     chdir($ctx->get_dest()) || die(sprintf("%s: %s\n", $ctx->get_dest(), $!));
+    # Extract any target category directories that are in .tar.gz
+    opendir(my $handle, '.');
+    while (my $name = readdir($handle)) {
+        if ((fileparse($name, '.tar.gz'))[2] eq '.tar.gz') {
+            my %value_of = %{$UTIL->shell_simple([qw{tar -x -z}, '-f', $name])};
+            if ($value_of{'rc'} == 0) {
+                unlink($name);
+            }
+        }
+    }
+    closedir($handle);
     # Determines the destination search path
     my $id = $ctx->get_id();
     @{$ctx->get_dests()} = (
@@ -647,6 +700,7 @@ sub _targets_update {
     # Back to original working directory
     chdir($old_cwd) || die(sprintf("%s: %s\n", $old_cwd, $!));
     if ($e) {
+        _finally($attrib_ref, $m_ctx, $ctx);
         die($e);
     }
     # Finally
@@ -678,8 +732,10 @@ sub _targets_update {
             FCM::Context::Event->MAKE_BUILD_TARGETS_FAIL,
             \@failed_targets
         );
+        _finally($attrib_ref, $m_ctx, $ctx);
         die("\n");
     }
+    _finally($attrib_ref, $m_ctx, $ctx);
 }
 
 # Updates a target.
@@ -738,7 +794,7 @@ sub _targets_manager_funcs {
                 _target_prep($state, $ctx);
                 $state->set_value($STATE->PENDING);
                 # Adds tasks that can be triggered by this task
-                for my $key (@{$target->get_triggers()}) {
+                for my $key (sort @{$target->get_triggers()}) {
                     if (    exists($state_hash_ref->{$key})
                         &&  !$state_hash_ref->{$key}->is_done()
                         &&  !grep {$_->get_id() eq $key} @{$stack_ref}
@@ -1103,7 +1159,11 @@ sub _targets_select {
         );
         my $target = $target_of{$key};
         DEP:
-        for (grep {$_->[0] ne $key} @{$target->get_deps()}) {
+        for (
+            grep {$_->[0] ne $key}
+            sort {$a->[0] cmp $b->[0]}
+            @{$target->get_deps()}
+        ) {
             my ($dep_key, $dep_type, $dep_remark) = @{$_};
             # Duplicated targets
             if (exists($targets_of{$dep_key})) {
@@ -1197,12 +1257,13 @@ sub _targets_select {
         }
     }
     # Walk the tree and report it
-    my @report_items = map {[$_]} @target_keys;
+    my @report_items = map {[$_]} sort @target_keys;
     my %reported;
     ITEM:
     while (my $item = pop(@report_items)) {
         my ($key, @stack) = @{$item};
-        my @deps = @{$state_of{$key}->get_deps()};
+        my @deps = sort {$a->[0]->get_key() cmp $b->[0]->get_key()}
+            @{$state_of{$key}->get_deps()};
         my @more_items = reverse(map {[$_->[0]->get_key(), @stack, $key]} @deps);
         my $n_more_items;
         if (exists($reported{$key})) {
@@ -1252,7 +1313,7 @@ sub _targets_select {
 sub _target_deps_are_done {
     my ($state, $state_hash_ref, $stack_ref) = @_;
     my @deps = map {[$_->[0]->get_key(), $_->[1]]} @{$state->get_deps()};
-    for my $k (grep {$state_hash_ref->{$_}->is_ready()} map {$_->[0]} @deps) {
+    for my $k (sort grep {$state_hash_ref->{$_}->is_ready()} map {$_->[0]} @deps) {
         if (!grep {$_->get_id() eq $k} @{$stack_ref}) {
             push(@{$stack_ref}, $state_hash_ref->{$k});
         }
@@ -1449,16 +1510,21 @@ sub _target_update_ok {
     my $state = $state_hash_ref->{$key};
     $state->set_value($STATE->DONE);
     # If this target is needed by other targets...
+    my @released_pending_states;
     while (my ($k, $s) = each(%{$state->get_needed_by()})) {
         my $pending_for_ref = $s->get_pending_for();
         delete($pending_for_ref->{$key});
         if ($s->is_pending() && !keys(%{$pending_for_ref})) {
             $s->set_value($STATE->READY);
             if (!grep {$_->get_id() eq $k} @{$stack_ref}) {
-                push(@{$stack_ref}, $s);
+                push(@released_pending_states, $s);
             }
         }
     }
+    push(
+        @{$stack_ref},
+        sort {$a->get_id() cmp $b->get_id()} @released_pending_states,
+    );
     if (defined($elapsed_time)) { # Done target update
         my $target0 = $ctx->get_target_of()->{$target->get_key()};
         $target0->set_info_of({}); # unset
@@ -1511,6 +1577,32 @@ sub _prev_hash_item_getter {
     sub {exists($p_item_of{$_[0]}) ? $p_item_of{$_[0]} : undef};
 }
 
+# Perform final actions.
+# Archive intermediate target directories if necessary.
+sub _finally {
+    my ($attrib_ref, $m_ctx, $ctx) = @_;
+    if (!$m_ctx->get_option_of('archive')) {
+        return;
+    }
+    my %can_archive = map {($_ => 1)} _props(
+        $attrib_ref, 'archive-ok-target-category', $ctx);
+    opendir(my $handle, $ctx->get_dest());
+    while (my $name = readdir($handle)) {
+        if ($can_archive{$name}) {
+            my @command = (
+                qw{tar -c -z}, '-C', $ctx->get_dest(),
+                '-f', catfile($ctx->get_dest(), $name . '.tar.gz'),
+                $name,
+            );
+            my %value_of = %{$UTIL->shell_simple(\@command)};
+            if ($value_of{'rc'} == 0) {
+                rmtree(catfile($ctx->get_dest(), $name));
+            }
+        }
+    }
+    closedir($handle);
+}
+
 # ------------------------------------------------------------------------------
 package FCM::System::Make::Build::State;
 use base qw{FCM::Class::HASH};
diff --git a/lib/FCM/System/Make/Build/FileType.pm b/lib/FCM/System/Make/Build/FileType.pm
index 5eee9b3..85de594 100644
--- a/lib/FCM/System/Make/Build/FileType.pm
+++ b/lib/FCM/System/Make/Build/FileType.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/FileType/C.pm b/lib/FCM/System/Make/Build/FileType/C.pm
index bd0a99e..b170d27 100644
--- a/lib/FCM/System/Make/Build/FileType/C.pm
+++ b/lib/FCM/System/Make/Build/FileType/C.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/FileType/CPP.pm b/lib/FCM/System/Make/Build/FileType/CPP.pm
index 54587d4..def1e5d 100644
--- a/lib/FCM/System/Make/Build/FileType/CPP.pm
+++ b/lib/FCM/System/Make/Build/FileType/CPP.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/FileType/CXX.pm b/lib/FCM/System/Make/Build/FileType/CXX.pm
index c7d2a8a..9639338 100644
--- a/lib/FCM/System/Make/Build/FileType/CXX.pm
+++ b/lib/FCM/System/Make/Build/FileType/CXX.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/FileType/Data.pm b/lib/FCM/System/Make/Build/FileType/Data.pm
index c97e986..045e2a3 100644
--- a/lib/FCM/System/Make/Build/FileType/Data.pm
+++ b/lib/FCM/System/Make/Build/FileType/Data.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/FileType/FPP.pm b/lib/FCM/System/Make/Build/FileType/FPP.pm
index 61bc67e..2a26741 100644
--- a/lib/FCM/System/Make/Build/FileType/FPP.pm
+++ b/lib/FCM/System/Make/Build/FileType/FPP.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/FileType/Fortran.pm b/lib/FCM/System/Make/Build/FileType/Fortran.pm
index beb6fed..88a40bf 100644
--- a/lib/FCM/System/Make/Build/FileType/Fortran.pm
+++ b/lib/FCM/System/Make/Build/FileType/Fortran.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/FileType/H.pm b/lib/FCM/System/Make/Build/FileType/H.pm
index eebef0c..4aedc58 100644
--- a/lib/FCM/System/Make/Build/FileType/H.pm
+++ b/lib/FCM/System/Make/Build/FileType/H.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/FileType/NS.pm b/lib/FCM/System/Make/Build/FileType/NS.pm
index e6c1eea..9d71f81 100644
--- a/lib/FCM/System/Make/Build/FileType/NS.pm
+++ b/lib/FCM/System/Make/Build/FileType/NS.pm
@@ -1,5 +1,5 @@
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/FileType/Script.pm b/lib/FCM/System/Make/Build/FileType/Script.pm
index aa466b3..5c4de19 100644
--- a/lib/FCM/System/Make/Build/FileType/Script.pm
+++ b/lib/FCM/System/Make/Build/FileType/Script.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/Task/Archive.pm b/lib/FCM/System/Make/Build/Task/Archive.pm
index e486483..c01be70 100644
--- a/lib/FCM/System/Make/Build/Task/Archive.pm
+++ b/lib/FCM/System/Make/Build/Task/Archive.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/Task/Compile.pm b/lib/FCM/System/Make/Build/Task/Compile.pm
index cf33d26..ac71222 100644
--- a/lib/FCM/System/Make/Build/Task/Compile.pm
+++ b/lib/FCM/System/Make/Build/Task/Compile.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/Task/Compile/C.pm b/lib/FCM/System/Make/Build/Task/Compile/C.pm
index 7fc470c..ddd432d 100644
--- a/lib/FCM/System/Make/Build/Task/Compile/C.pm
+++ b/lib/FCM/System/Make/Build/Task/Compile/C.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/Task/Compile/CXX.pm b/lib/FCM/System/Make/Build/Task/Compile/CXX.pm
index 7f7e509..0afdae9 100644
--- a/lib/FCM/System/Make/Build/Task/Compile/CXX.pm
+++ b/lib/FCM/System/Make/Build/Task/Compile/CXX.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/Task/Compile/Fortran.pm b/lib/FCM/System/Make/Build/Task/Compile/Fortran.pm
index abee5d4..88b6fb9 100644
--- a/lib/FCM/System/Make/Build/Task/Compile/Fortran.pm
+++ b/lib/FCM/System/Make/Build/Task/Compile/Fortran.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/Task/ExtractInterface.pm b/lib/FCM/System/Make/Build/Task/ExtractInterface.pm
index 82e602d..366f867 100644
--- a/lib/FCM/System/Make/Build/Task/ExtractInterface.pm
+++ b/lib/FCM/System/Make/Build/Task/ExtractInterface.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -306,7 +306,7 @@ sub _process {
     # Attribute Statements
     ($name) = $statement->{value} =~ $RE{TYPE_ATTR};
     if ($name) {
-        $statement->{name} = $name;
+        $statement->{name} = lc($name);
         $statement->{type} = 'attr';
     }
 }
@@ -407,7 +407,7 @@ STATEMENT:
         }
         if ($statement->{type} eq 'attr') {
             my ($spec, @tokens) = ($statement->{value} =~ /$RE{NAME_COMP}/g);
-            if (grep { exists($token_set{$_}) } @tokens) {
+            if (grep { exists($token_set{lc($_)}) } @tokens) {
                 for my $token (@tokens) {
                     $token_set{$token} = 1;
                 }
diff --git a/lib/FCM/System/Make/Build/Task/Install.pm b/lib/FCM/System/Make/Build/Task/Install.pm
index 45bd1b0..0c0a446 100644
--- a/lib/FCM/System/Make/Build/Task/Install.pm
+++ b/lib/FCM/System/Make/Build/Task/Install.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/Task/Link.pm b/lib/FCM/System/Make/Build/Task/Link.pm
index 5ab63da..84e6959 100644
--- a/lib/FCM/System/Make/Build/Task/Link.pm
+++ b/lib/FCM/System/Make/Build/Task/Link.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/Task/Link/C.pm b/lib/FCM/System/Make/Build/Task/Link/C.pm
index 99ebef3..994439d 100644
--- a/lib/FCM/System/Make/Build/Task/Link/C.pm
+++ b/lib/FCM/System/Make/Build/Task/Link/C.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/Task/Link/CXX.pm b/lib/FCM/System/Make/Build/Task/Link/CXX.pm
index 1c5848c..c8f2825 100644
--- a/lib/FCM/System/Make/Build/Task/Link/CXX.pm
+++ b/lib/FCM/System/Make/Build/Task/Link/CXX.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/Task/Link/Fortran.pm b/lib/FCM/System/Make/Build/Task/Link/Fortran.pm
index 94e8cb4..1dc0ff9 100644
--- a/lib/FCM/System/Make/Build/Task/Link/Fortran.pm
+++ b/lib/FCM/System/Make/Build/Task/Link/Fortran.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/Task/Preprocess.pm b/lib/FCM/System/Make/Build/Task/Preprocess.pm
index 2147d7b..994c226 100644
--- a/lib/FCM/System/Make/Build/Task/Preprocess.pm
+++ b/lib/FCM/System/Make/Build/Task/Preprocess.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/Task/Preprocess/C.pm b/lib/FCM/System/Make/Build/Task/Preprocess/C.pm
index 75961fb..a3179a0 100644
--- a/lib/FCM/System/Make/Build/Task/Preprocess/C.pm
+++ b/lib/FCM/System/Make/Build/Task/Preprocess/C.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/Task/Preprocess/Fortran.pm b/lib/FCM/System/Make/Build/Task/Preprocess/Fortran.pm
index f093f43..2851b5b 100644
--- a/lib/FCM/System/Make/Build/Task/Preprocess/Fortran.pm
+++ b/lib/FCM/System/Make/Build/Task/Preprocess/Fortran.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Build/Task/Share.pm b/lib/FCM/System/Make/Build/Task/Share.pm
index 4625b37..92448b2 100644
--- a/lib/FCM/System/Make/Build/Task/Share.pm
+++ b/lib/FCM/System/Make/Build/Task/Share.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Extract.pm b/lib/FCM/System/Make/Extract.pm
index bcff360..f081c9f 100644
--- a/lib/FCM/System/Make/Extract.pm
+++ b/lib/FCM/System/Make/Extract.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -34,7 +34,7 @@ use File::Basename qw{dirname};
 use File::Compare qw{compare};
 use File::Copy qw{copy};
 use File::Path qw{mkpath rmtree};
-use File::Spec::Functions qw{catfile tmpdir};
+use File::Spec::Functions qw{abs2rel catfile tmpdir};
 use File::Temp;
 use List::Util qw{first};
 use Storable qw{dclone};
@@ -76,6 +76,7 @@ __PACKAGE__->class(
             config_unparse            => \&_config_unparse,
             config_unparse_class_prop => \&_config_unparse_class_prop,
             ctx                       => \&_ctx,
+            ctx_load_hook             => \&_ctx_load_hook,
             main                      => \&_main,
         },
     },
@@ -209,15 +210,20 @@ sub _config_parse_location_primary {
             $ctx->get_project_of()->{$ns} = $ctx->CTX_PROJECT->new({ns => $ns});
         }
         my $project = $ctx->get_project_of()->{$ns};
-        if ($project->get_inherited()) {
-            if ($project->get_locator()->get_value() ne $entry->get_value()) {
-                return $E->throw($E->CONFIG_CONFLICT, $entry);
-            }
-        }
-        elsif ($entry->get_value()) {
-            $project->set_locator(
-                FCM::Context::Locator->new($entry->get_value(), \%option),
+        if ($entry->get_value()) {
+            my $locator = FCM::Context::Locator->new(
+                $entry->get_value(), \%option,
             );
+            $attrib_ref->{util}->loc_as_normalised($locator);
+            if ($project->get_inherited()) {
+                my $project_locator = $project->get_locator();
+                if ($project_locator->get_value() ne $locator->get_value()) {
+                    return $E->throw($E->CONFIG_CONFLICT, $entry);
+                }
+            }
+            else {
+                $project->set_locator($locator);
+            }
         }
         else {
             $project->set_locator(undef);
@@ -387,6 +393,56 @@ sub _ctx {
     FCM::Context::Make::Extract->new({id => $id, id_of_class => $id_of_class});
 }
 
+# Hook when loading a previous ctx.
+sub _ctx_load_hook {
+    my ($attrib_ref, $old_m_ctx, $old_ctx, $old_m_dest, $old_dest) = @_;
+    my $path_mod_func = sub {
+        my ($get_func, $set_func) = @_;
+        my $path = $get_func->();
+        if (!defined($path)) {
+            return;
+        }
+        my $rel_path = abs2rel($path, $old_m_dest);
+        if (index($rel_path, '..') != 0) {
+            $set_func->(catfile($old_m_ctx->get_dest(), $rel_path));
+        }
+    };
+    while (my ($ns, $project) = each(%{$old_ctx->get_project_of()})) {
+        $path_mod_func->(
+            sub {$project->get_cache()},
+            sub {$project->set_cache(@_)},
+        );
+        for my $tree (@{$project->get_trees()}) {
+            $path_mod_func->(
+                sub {$tree->get_cache()},
+                sub {$tree->set_cache(@_)},
+            );
+            for my $source (@{$tree->get_sources()}) {
+                $path_mod_func->(
+                    sub {$source->get_cache()},
+                    sub {$source->set_cache(@_)},
+                );
+            }
+        }
+    }
+    while (my ($key, $target) = each(%{$old_ctx->get_target_of()})) {
+        $path_mod_func->(
+            sub {$target->get_path()},
+            sub {$target->set_path(@_)},
+        );
+        $path_mod_func->(
+            sub {$target->get_dests()->[0]},
+            sub {$target->get_dests()->[0] = $_[0]},
+        );
+        while (my ($ns, $source) = each(%{$target->get_source_of()})) {
+            $path_mod_func->(
+                sub {$source->get_cache()},
+                sub {$source->set_cache(@_)},
+            );
+        }
+    }
+}
+
 # The main function of this class.
 sub _main {
     my ($attrib_ref, $m_ctx, $ctx) = @_;
@@ -775,6 +831,20 @@ sub _extract_incremental {
 # Updates the project tree caches.
 sub _project_tree_caches_update {
     my ($attrib_ref, $m_ctx, $ctx) = @_;
+    # If previous cache in .tar.gz, extract it
+    my $cache_tar_gz = $attrib_ref->{shared_util_of}{dest}->path(
+        $m_ctx, 'sys-cache', $ctx->get_id() . '.tar.gz',
+    );
+    if (-f $cache_tar_gz) {
+        my @command = (
+            qw{tar -x -z}, '-C', dirname($cache_tar_gz), '-f', $cache_tar_gz,
+        );
+        my %value_of = %{$UTIL->shell_simple(\@command)};
+        if ($value_of{'rc'} == 0) {
+            unlink($cache_tar_gz);
+        }
+    }
+    # Start the parallel task runner to do project tree caches update
     my $timer = $UTIL->timer();
     my $n_jobs = $m_ctx->get_option_of('jobs');
     my $n_trees = scalar(
@@ -803,6 +873,7 @@ sub _project_tree_caches_update {
     my $e = $@;
     $runner->destroy();
     if ($e) {
+        _finally($attrib_ref, $m_ctx, $ctx);
         die($e);
     }
     $UTIL->event(
@@ -944,34 +1015,41 @@ sub _symlink_handle {
 sub _targets_update {
     my ($attrib_ref, $m_ctx, $ctx) = @_;
     my %basket_of = (status => {}, status_of_source => {});
-    while (my ($ns, $target) = each(%{$ctx->get_target_of()})) {
-        if ($target->get_status() eq $target->ST_UNKNOWN) {
-            my %source_of = %{$target->get_source_of()};
-            my $handler
-                = keys(%source_of) ? \&_target_update
-                :                    \&_target_delete
-                ;
-            $handler->($attrib_ref, $m_ctx, $ctx, $target);
-            my $base = delete($source_of{0});
-            my @diffs = grep {!$_->is_unchanged()} values(%source_of);
-            $target->set_status_of_source(
-                  !keys(%{$target->get_source_of()}) ? $target->ST_UNKNOWN
-                : $base->is_missing()                ? $target->ST_ADDED
-                : (grep {$_->is_missing()} @diffs)   ? $target->ST_DELETED
-                : scalar(@diffs) > 1                 ? $target->ST_MERGED
-                : scalar(@diffs)                     ? $target->ST_MODIFIED
-                :                                      $target->ST_UNCHANGED
-            );
-            $UTIL->event(
-                FCM::Context::Event->MAKE_EXTRACT_TARGET, $target,
-            );
+    eval {
+        while (my ($ns, $target) = each(%{$ctx->get_target_of()})) {
+            if ($target->get_status() eq $target->ST_UNKNOWN) {
+                my %source_of = %{$target->get_source_of()};
+                my $handler
+                    = keys(%source_of) ? \&_target_update
+                    :                    \&_target_delete
+                    ;
+                $handler->($attrib_ref, $m_ctx, $ctx, $target);
+                my $base = delete($source_of{0});
+                my @diffs = grep {!$_->is_unchanged()} values(%source_of);
+                $target->set_status_of_source(
+                      !keys(%{$target->get_source_of()}) ? $target->ST_UNKNOWN
+                    : $base->is_missing()                ? $target->ST_ADDED
+                    : (grep {$_->is_missing()} @diffs)   ? $target->ST_DELETED
+                    : scalar(@diffs) > 1                 ? $target->ST_MERGED
+                    : scalar(@diffs)                     ? $target->ST_MODIFIED
+                    :                                      $target->ST_UNCHANGED
+                );
+                $UTIL->event(
+                    FCM::Context::Event->MAKE_EXTRACT_TARGET, $target,
+                );
+            }
+            $basket_of{status}{$target->get_status()}++;
+            $basket_of{status_of_source}{$target->get_status_of_source()}++;
         }
-        $basket_of{status}{$target->get_status()}++;
-        $basket_of{status_of_source}{$target->get_status_of_source()}++;
+    };
+    if (my $e = $@) {
+        _finally($attrib_ref, $m_ctx, $ctx);
+        die($e);
     }
     $UTIL->event(
         FCM::Context::Event->MAKE_EXTRACT_TARGET_SUMMARY, \%basket_of,
     );
+    _finally($attrib_ref, $m_ctx, $ctx);
 }
 
 # Updates a deleted target.
@@ -1122,6 +1200,28 @@ sub _target_update_source_merge {
     return $path_of_mine;
 }
 
+# Perform final actions.
+# Archive cache directory if necessary.
+sub _finally {
+    my ($attrib_ref, $m_ctx, $ctx) = @_;
+    if (!$m_ctx->get_option_of('archive')) {
+        return;
+    }
+    my $cache = $attrib_ref->{shared_util_of}{dest}->path(
+        $m_ctx, 'sys-cache', $ctx->get_id(),
+    );
+    if (-d $cache) {
+        my @command = (
+            qw{tar -c -z}, '-C', dirname($cache), '-f', $cache . '.tar.gz',
+            $ctx->get_id(),
+        );
+        my %value_of = %{$UTIL->shell_simple(\@command)};
+        if ($value_of{'rc'} == 0) {
+            rmtree($cache);
+        }
+    }
+}
+
 # In scalar context, returns true if the contents or permissions of 2 paths
 # differ. In array context, returns ($is_diff_in_perms, $is_diff_in_content).
 sub _compare {
diff --git a/lib/FCM/System/Make/Mirror.pm b/lib/FCM/System/Make/Mirror.pm
index b1e117b..c9c4d30 100644
--- a/lib/FCM/System/Make/Mirror.pm
+++ b/lib/FCM/System/Make/Mirror.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -47,6 +47,7 @@ our %CONFIG_PARSER_OF = (
 
 # Default properties
 our %PROP_OF = (
+    'config-file.name'  => [q{}],
     'config-file.steps' => [q{}],
     'no-config-file'    => [q{}],
 );
@@ -167,6 +168,7 @@ sub _mirror_config_file {
     my ($attrib_ref, $m_ctx, $ctx, $sources_ref) = @_;
     my ($target) = _target_and_authority($ctx);
     my $mirror_m_ctx = FCM::Context::Make->new({dest => '$HERE'});
+    $mirror_m_ctx->set_name(_prop($attrib_ref, 'config-file.name', $ctx));
     my %no_inherit_from;
     if (@{$m_ctx->get_inherit_ctx_list()}) {
         # Inherited destinations
@@ -237,11 +239,22 @@ sub _mirror_config_file {
     # Saves the configuration file
     my @lines = map {$_ . "\n"}
         $attrib_ref->{shared_util_of}{config}->unparse($mirror_m_ctx);
-    my $path = $attrib_ref->{shared_util_of}{dest}->path($ctx, 'config');
+    my $DEST_UTIL = $attrib_ref->{shared_util_of}{dest};
+    my $path = $DEST_UTIL->path(
+        {   'dest' => $ctx->get_dest(),
+            'name' => _prop($attrib_ref, 'config-file.name', $ctx),
+        },
+        'config',
+    );
     $attrib_ref->{util}->file_save($path, \@lines);
     _mirror(
         $attrib_ref, $m_ctx, $ctx,
-        [$path], $attrib_ref->{shared_util_of}{dest}->path($target, 'config'),
+        [$path], $DEST_UTIL->path(
+            {   'dest' => $target,
+                'name' => _prop($attrib_ref, 'config-file.name', $ctx),
+            },
+            'config',
+        ),
     );
 }
 
@@ -288,13 +301,24 @@ sub _mirror_orig_config_file {
         ),
         map {$_ . "\n"} $attrib_ref->{shared_util_of}{config}->unparse($m_ctx),
     );
-    my $path = $attrib_ref->{shared_util_of}{dest}->path($ctx, 'config-orig');
+    my $DEST_UTIL = $attrib_ref->{shared_util_of}{dest};
+    my $path = $DEST_UTIL->path(
+        {   'dest' => $ctx->get_dest(),
+            'name' => _prop($attrib_ref, 'config-file.name', $ctx),
+        },
+        'config-orig',
+    );
     $attrib_ref->{util}->file_save($path, \@lines);
     my ($target) = _target_and_authority($ctx);
     _mirror(
         $attrib_ref, $m_ctx, $ctx,
         [$path],
-        $attrib_ref->{shared_util_of}{dest}->path($target, 'config-orig'),
+        $DEST_UTIL->path(
+            {   'dest' => $target,
+                'name' => _prop($attrib_ref, 'config-file.name', $ctx),
+            },
+            'config-orig',
+        ),
     );
 }
 
diff --git a/lib/FCM/System/Make/Preprocess.pm b/lib/FCM/System/Make/Preprocess.pm
index 890c6b3..aebec0e 100644
--- a/lib/FCM/System/Make/Preprocess.pm
+++ b/lib/FCM/System/Make/Preprocess.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Make/Share/Config.pm b/lib/FCM/System/Make/Share/Config.pm
index ec2639a..5fc7b39 100644
--- a/lib/FCM/System/Make/Share/Config.pm
+++ b/lib/FCM/System/Make/Share/Config.pm
@@ -1,5 +1,5 @@
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -37,9 +37,10 @@ my $E = 'FCM::System::Exception';
 # Configuration parser label to action map
 my %CONFIG_PARSER_OF = (
     'dest'       => \&_parse_dest,
-    'use'        => \&_parse_use,
+    'name'       => \&_parse_name,
     'step.class' => \&_parse_step_class,
     'steps'      => \&_parse_steps,
+    'use'        => \&_parse_use,
 );
 
 __PACKAGE__->class(
@@ -51,6 +52,7 @@ __PACKAGE__->class(
 # populate the context of the current make.
 sub _parse {
     my ($attrib_ref, $entry_callback_ref, $m_ctx, @args) = @_;
+    my $DEST_UTIL = $attrib_ref->{shared_util_of}{dest};
     my $dir = $m_ctx->get_option_of('directory')
         ? $m_ctx->get_option_of('directory') : cwd();
     my $dir_locator = FCM::Context::Locator->new($dir);
@@ -64,8 +66,8 @@ sub _parse {
     for my $config_file_name (@config_file_names) {
         my $is_specified_name = 1;
         if (!defined($config_file_name)) {
-            $config_file_name
-                = $attrib_ref->{shared_util_of}{dest}->path_of('config');
+            $config_file_name = $DEST_UTIL->path(
+                {'name' => $m_ctx->get_name()}, 'config');
             $is_specified_name = 0;
         }
         if (    $attrib_ref->{util}->uri_match($config_file_name)
@@ -98,8 +100,9 @@ sub _parse {
         }
     }
     if (!@config_reader_refs) {
-        my $config_file_name = $attrib_ref->{shared_util_of}{dest}->path(
-            $dir_locator->get_value(), 'config',
+        my $config_file_name = $DEST_UTIL->path(
+            {'dest' => $dir_locator->get_value(), 'name' => $m_ctx->get_name()},
+            'config',
         );
         if (-f $config_file_name) {
             push(@config_reader_refs, _get_config_reader(
@@ -202,12 +205,18 @@ sub _get_config_reader {
     );
 }
 
-# Reads the dest declaration.
+# Reads the "dest" declaration from a config entry.
 sub _parse_dest {
     my ($attrib_ref, $m_ctx, $entry) = @_;
     $m_ctx->set_dest($entry->get_value());
 }
 
+# Reads the "name" declaration from a config entry.
+sub _parse_name {
+    my ($attrib_ref, $m_ctx, $entry) = @_;
+    $m_ctx->set_name($entry->get_value());
+}
+
 # Reads the step.class declaration from a config entry.
 sub _parse_step_class {
     my ($attrib_ref, $m_ctx, $entry) = @_;
@@ -246,16 +255,11 @@ sub _parse_use {
     my $inherit_ctx_list_ref = $m_ctx->get_inherit_ctx_list();
     for my $value ($entry->get_values()) {
         $value = $attrib_ref->{util}->file_tilde_expand($value);
-        my $i_m_ctx = eval {
-            $DEST->ctx_load(
-                $DEST->path($value, 'sys-ctx'),
-                blessed($m_ctx),
-            );
-        };
-        if (!defined($i_m_ctx) && (my $e = $@)) {
+        my $i_m_ctx = eval {$DEST->ctx_load($m_ctx, $value)};
+        if (my $e = $@) {
             return $E->throw($E->CONFIG_VALUE, $entry, $e);
         }
-        if ($i_m_ctx->get_status() != $i_m_ctx->ST_OK) {
+        if (!defined($i_m_ctx) || $i_m_ctx->get_status() != $i_m_ctx->ST_OK) {
             return $E->throw($E->CONFIG_INHERIT, $entry);
         }
         push(@{$m_ctx->get_inherit_ctx_list()}, $i_m_ctx);
@@ -306,8 +310,9 @@ sub _unparse {
                         : ()
                     ;
                 }
-            (   [\&_unparse_use     , 'use'  ],
-                [\&_unparse_steps   , 'steps'],
+            (   [sub {$m_ctx->get_name()}, 'name' ],
+                [\&_unparse_use          , 'use'  ],
+                [\&_unparse_steps        , 'steps'],
                 [sub {$m_ctx->get_dest()}, 'dest' ],
             ),
         ),
diff --git a/lib/FCM/System/Make/Share/Dest.pm b/lib/FCM/System/Make/Share/Dest.pm
index c3f4ad6..d08b789 100644
--- a/lib/FCM/System/Make/Share/Dest.pm
+++ b/lib/FCM/System/Make/Share/Dest.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -32,26 +32,26 @@ use File::Spec::Functions qw{catfile rel2abs};
 use IO::File;
 use IO::Uncompress::Gunzip qw{gunzip};
 use IO::Compress::Gzip qw{gzip};
-use Scalar::Util qw{blessed};
+use Scalar::Util qw{blessed reftype};
 use Storable qw{fd_retrieve nstore_fd};
 use Sys::Hostname qw{hostname};
 
 # The relative paths for locating files in a destination
 our %PATH_OF = (
-    'config'                        => 'fcm-make.cfg',
-    'config-orig'                   => 'fcm-make.cfg.orig',
-    'sys'                           => '.fcm-make',
-    'sys-cache'                     => '.fcm-make/cache',
-    'sys-config-as-parsed'          => '.fcm-make/config-as-parsed.cfg',
-    'sys-config-as-parsed-symlink'  => 'fcm-make-as-parsed.cfg',
-    'sys-config-on-success'         => '.fcm-make/config-on-success.cfg',
-    'sys-config-on-success-symlink' => 'fcm-make-on-success.cfg',
-    'sys-ctx-uncompressed'          => '.fcm-make/ctx',
-    'sys-ctx'                       => '.fcm-make/ctx.gz',
-    'sys-log'                       => '.fcm-make/log',
-    'sys-log-symlink'               => 'fcm-make.log',
-    'sys-lock'                      => 'fcm-make.lock',
-    'sys-lock-info'                 => 'fcm-make.lock/info.txt',
+    'config'                        => 'fcm-make%s.cfg',
+    'config-orig'                   => 'fcm-make%s.cfg.orig',
+    'sys'                           => '.fcm-make%s',
+    'sys-cache'                     => '.fcm-make%s/cache',
+    'sys-config-as-parsed'          => '.fcm-make%s/config-as-parsed.cfg',
+    'sys-config-as-parsed-symlink'  => 'fcm-make%s-as-parsed.cfg',
+    'sys-config-on-success'         => '.fcm-make%s/config-on-success.cfg',
+    'sys-config-on-success-symlink' => 'fcm-make%s-on-success.cfg',
+    'sys-ctx-uncompressed'          => '.fcm-make%s/ctx',
+    'sys-ctx'                       => '.fcm-make%s/ctx.gz',
+    'sys-log'                       => '.fcm-make%s/log',
+    'sys-log-symlink'               => 'fcm-make%s.log',
+    'sys-lock'                      => 'fcm-make%s.lock',
+    'sys-lock-info'                 => 'fcm-make%s.lock/info.txt',
     'target'                        => '',
 );
 
@@ -71,14 +71,36 @@ my %ACTION_OF = (
 
 # Creates the class.
 __PACKAGE__->class(
-    {path_of => {isa => '%', default => {%PATH_OF}}, util => '&'},
+    {   path_of        => {isa => '%', default => {%PATH_OF}},
+        shared_util_of => '%',
+        subsystem_of   => '%',
+        util           => '&',
+    },
     {action_of => \%ACTION_OF},
 );
 
 # Loads a storable context from a path.
 sub _ctx_load {
-    my ($attrib_ref, $path, $expected_class) = @_;
-    my $ctx = eval {
+    my ($attrib_ref, $m_ctx, $from) = @_;
+    my $path;
+    my $dest;
+    if ($from) {
+        NAME:
+        for my $name ($m_ctx->get_name(), undef) {
+            $path = _path(
+                $attrib_ref, {'dest' => $from, 'name' => $name}, 'sys-ctx');
+
+            if (-f $path) {
+                $dest = $from;
+                last NAME;
+            }
+        }
+    }
+    else {
+        $path = _path($attrib_ref, $m_ctx, 'sys-ctx');
+        $dest = $m_ctx->get_dest();
+    }
+    my $old_m_ctx = eval {
         my $handle = IO::File->new_tmpfile();
         gunzip($path, $handle) || die($!);
         $handle->seek(0, 0);
@@ -87,10 +109,42 @@ sub _ctx_load {
     if (my $e = $@) {
         return $E->throw($E->CACHE_LOAD, $path, $e);
     }
-    if (!$ctx || !$ctx->isa($expected_class)) {
+    if (    !$old_m_ctx
+        ||  !$old_m_ctx->isa(blessed($m_ctx))
+        ||  (       defined($old_m_ctx->get_name())
+                &&  $old_m_ctx->get_name() ne $m_ctx->get_name()
+            )
+    ) {
         return $E->throw($E->CACHE_TYPE, $path);
     }
-    return $ctx;
+    my $new_m_dest = rel2abs($dest);
+    if ($new_m_dest ne $old_m_ctx->get_dest()) {
+        my $old_m_dest = $old_m_ctx->get_dest();
+        $old_m_ctx->set_dest($new_m_dest);
+        $old_m_ctx->set_dest_lock(undef);
+        SUBSYSTEM:
+        while (my ($id, $old_ctx) = each(%{$old_m_ctx->get_ctx_of()})) {
+            my $id_of_class = $old_ctx->get_id_of_class();
+            if (exists($attrib_ref->{'subsystem_of'}{$id_of_class})) {
+                my $subsystem = $attrib_ref->{'subsystem_of'}{$id_of_class};
+                if (!$old_ctx->can('set_dest')) {
+                    next SUBSYSTEM;
+                }
+                my $old_dest = $old_ctx->get_dest();
+                $old_ctx->set_dest(_path(
+                    $attrib_ref,
+                    {'dest' => $new_m_dest, 'name' => $m_ctx->get_name()},
+                    'target',
+                    $old_ctx->get_id(),
+                ));
+                if ($subsystem->can('ctx_load_hook')) {
+                    $subsystem->ctx_load_hook(
+                        $old_m_ctx, $old_ctx, $old_m_dest, $old_dest);
+                }
+            }
+        }
+    }
+    return $old_m_ctx;
 }
 
 # Finalises the destination of a make context.
@@ -101,6 +155,8 @@ sub _dest_done {
     }
     my $dest = _path($attrib_ref, $m_ctx, 'sys-ctx-uncompressed');
     my $dest_parent = dirname($dest);
+    my $dest_lock = $m_ctx->get_dest_lock();
+    $m_ctx->set_dest_lock(undef);
     if (-d $dest_parent) {
         eval {
             my $handle = IO::File->new_tmpfile();
@@ -119,8 +175,8 @@ sub _dest_done {
     ) {
         _tidy($attrib_ref, $path);
     }
-    if ($m_ctx->get_dest_lock()) {
-        rmtree($m_ctx->get_dest_lock());
+    if ($dest_lock) {
+        rmtree($dest_lock);
     }
 }
 
@@ -175,12 +231,11 @@ sub _dest_init {
         }
     }
     # Loads context of previous make, if possible
-    my $prev_m_ctx = eval {
-        my $path = _path($attrib_ref, $m_ctx, 'sys-ctx');
-        -f $path ? _ctx_load($attrib_ref, $path, blessed($m_ctx)) : undef;
-    };
+    my $prev_m_ctx = eval {_ctx_load($attrib_ref, $m_ctx)};
     if (my $e = $@) {
-        if (!$E->caught($e) || $e->get_code() ne $E->CACHE_LOAD) {
+        if (    !$E->caught($e)
+            ||  !grep {$_ eq $e->get_code()} ($E->CACHE_LOAD, $E->CACHE_TYPE)
+        ) {
             die($e);
         }
         $@ = undef;
@@ -207,12 +262,15 @@ sub _dest_init {
 # Returns the path of a named item relative to the context destination.
 sub _path {
     my ($attrib_ref, $m_ctx, $key, @paths) = @_;
-    my $path
-        = blessed($m_ctx) && $m_ctx->can('get_dest') ? $m_ctx->get_dest()
-        : defined($m_ctx)                            ? $m_ctx
-        :                                              cwd()
-        ;
-    catfile($path, split(q{/}, $attrib_ref->{path_of}{$key}), @paths);
+    my %ctx = reftype($m_ctx) && reftype($m_ctx) eq 'HASH'
+        ? %{$m_ctx} : ('dest' => $m_ctx, 'name' => q{});
+    $ctx{'dest'} ||= q{};
+    $ctx{'name'} ||= q{};
+    catfile(
+        ($ctx{'dest'} ? $ctx{'dest'} : ()),
+        split(q{/}, sprintf($attrib_ref->{path_of}{$key}, $ctx{'name'})),
+        @paths,
+    );
 }
 
 # Returns an ARRAY reference containing the search paths of a named item
@@ -340,20 +398,21 @@ previous make of the system if necessary, and setting up the system directory.
 =item $instance->path($ctx,$key, at paths)
 
 Returns the path of a named item ($key) relative to $ctx, which can either be a
-blessed object with a $ctx->get_dest() method, a scalar path, or undef (in which
-case, cwd() is used). If @paths are specified, they are concatenated at the end
+HASH reference with {'dest' => $dest, 'name' => $name}, or a scalar path
+pointing to $dest, where $dest is the root of the path and $name is the name of
+the context. If @paths are specified, they are concatenated at the end
 of the path.
 
-=item $instance->path_of($key)
-
-Returns the value of the named item in a make destination.
-
 =item $instance->paths($ctx,$key, at paths)
 
 Returns an ARRAY reference containing the search paths of a named item ($key)
 relative to the destinations of $ctx and its inherited contexts. If @paths are
 specified, they are concatenated at the end of each returned path.
 
+=item $instance->path_of($key)
+
+Returns the template value of the named item in a make destination.
+
 =item $instance->save($item,$ctx,$key, at paths)
 
 Saves $item in a path given by $instance->path($ctx,$key, at paths). $item can be a
diff --git a/lib/FCM/System/Make/Share/Subsystem.pm b/lib/FCM/System/Make/Share/Subsystem.pm
index 3cda0c3..0802da0 100644
--- a/lib/FCM/System/Make/Share/Subsystem.pm
+++ b/lib/FCM/System/Make/Share/Subsystem.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Misc.pm b/lib/FCM/System/Misc.pm
index 3315f64..7237bab 100644
--- a/lib/FCM/System/Misc.pm
+++ b/lib/FCM/System/Misc.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/System/Old.pm b/lib/FCM/System/Old.pm
index f62b846..3e51799 100644
--- a/lib/FCM/System/Old.pm
+++ b/lib/FCM/System/Old.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Util.pm b/lib/FCM/Util.pm
index 2019eaa..17b6d4d 100644
--- a/lib/FCM/Util.pm
+++ b/lib/FCM/Util.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Util/ConfigReader.pm b/lib/FCM/Util/ConfigReader.pm
index 624f3ef..9f7dfb0 100644
--- a/lib/FCM/Util/ConfigReader.pm
+++ b/lib/FCM/Util/ConfigReader.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Util/ConfigUpgrade.pm b/lib/FCM/Util/ConfigUpgrade.pm
index fa4f86f..296fc55 100644
--- a/lib/FCM/Util/ConfigUpgrade.pm
+++ b/lib/FCM/Util/ConfigUpgrade.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Util/Event.pm b/lib/FCM/Util/Event.pm
index 7a16f54..7331f3b 100644
--- a/lib/FCM/Util/Event.pm
+++ b/lib/FCM/Util/Event.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -110,7 +110,6 @@ our %E_CM_FORMAT_FOR = (
     ST_OUT_OF_DATE    => "File(s) out of date:\n%s",
     SWITCH_UNSAFE     => "%s: merge template exists."
                          . " Please remove before retrying.\n",
-    WC_EXIST          => "%s: working copy already exists.\n",
     WC_INVALID_BRANCH => "%s: not a working copy of a standard FCM branch.\n",
     WC_URL_NOT_EXIST  => "%s: working copy URL does not exists at HEAD.\n",
 );
@@ -158,6 +157,7 @@ our %E_SYS_FORMATTER_FOR = (
     MAKE             => _format_e_func('e_sys_make'),
     MAKE_ARG         => \&_format_e_sys_make_arg,
     MAKE_CFG         => _format_e_func('e_sys_make_cfg'),
+    MAKE_CFG_FILE    => _format_e_func('e_sys_make_cfg_file'),
     MAKE_PROP_NS     => \&_format_e_sys_make_prop_ns,
     MAKE_PROP_VALUE  => \&_format_e_sys_make_prop_value,
     SHELL            => \&_format_e_sys_shell,
@@ -241,8 +241,9 @@ our %S = (
     e_sys_mirror_target          => '%s: cannot create mirror target',
     e_sys_make                   => '%s: step is not implemented',
     e_sys_make_arg               => 'arg %d (%s): invalid config declaration',
-    e_sys_make_cfg               => 'no configuration specified or found',
     e_sys_make_arg_more          => 'did you mean "%s"?',
+    e_sys_make_cfg               => 'no configuration specified or found',
+    e_sys_make_cfg_file          => '%s: no such configuration file',
     e_sys_make_prop_ns           => '%s.prop{%s}[%s] = %s: bad name-space',
     e_sys_make_prop_value        => '%s.prop{%s}[%s] = %s: bad value',
     e_sys_shell                  => '%s # rc=%d',
diff --git a/lib/FCM/Util/Exception.pm b/lib/FCM/Util/Exception.pm
index 92fe05b..d468155 100644
--- a/lib/FCM/Util/Exception.pm
+++ b/lib/FCM/Util/Exception.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Util/Locator.pm b/lib/FCM/Util/Locator.pm
index 74153a6..e8c98f4 100644
--- a/lib/FCM/Util/Locator.pm
+++ b/lib/FCM/Util/Locator.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Util/Locator/FS.pm b/lib/FCM/Util/Locator/FS.pm
index 719edce..58ce9c9 100644
--- a/lib/FCM/Util/Locator/FS.pm
+++ b/lib/FCM/Util/Locator/FS.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -67,16 +67,17 @@ sub _find {
         sub {
             $found ||= 1;
             my $path = $File::Find::name;
-            my ($vol, $dir_name, $base) = File::Spec->splitpath($path);
-            for my $name (File::Spec->splitdir($dir_name), $base) {
-                if (index($name, q{.}) == 0) {
-                    return; # ignore Unix hidden/system files
-                }
-            }
             my $ns = File::Spec->abs2rel($path, $value);
             if ($ns eq q{.}) {
                 $ns = q{};
             }
+            else {
+                for my $name (split(q{/}, $ns)) {
+                    if (index($name, q{.}) == 0) {
+                        return; # ignore Unix hidden/system files
+                    }
+                }
+            }
             my $last_mod_time = (-l $path ? lstat($path) : stat($path))[9];
             $callback->(
                 $path,
diff --git a/lib/FCM/Util/Locator/SSH.pm b/lib/FCM/Util/Locator/SSH.pm
index 33f4fd0..17dbc2c 100644
--- a/lib/FCM/Util/Locator/SSH.pm
+++ b/lib/FCM/Util/Locator/SSH.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -57,10 +57,10 @@ sub _can_work_with {
     if (!$value) {
         return;
     }
-    my ($auth) = split(':', $value, 2);
-    if (!$auth) {
+    if (index($value, ':') < 0) {
         return;
     }
+    my ($auth) = split(':', $value, 2);
     my $host = index($auth, '@') >= 0 ? (split('@', $auth, 2))[1] : $auth;
     $host ? gethostbyname($host) : undef;
 }
diff --git a/lib/FCM/Util/Locator/SVN.pm b/lib/FCM/Util/Locator/SVN.pm
index 3ea6477..d217165 100644
--- a/lib/FCM/Util/Locator/SVN.pm
+++ b/lib/FCM/Util/Locator/SVN.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Util/Reporter.pm b/lib/FCM/Util/Reporter.pm
index 492187c..87fd096 100644
--- a/lib/FCM/Util/Reporter.pm
+++ b/lib/FCM/Util/Reporter.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Util/Shell.pm b/lib/FCM/Util/Shell.pm
index 1b50c22..d5353d9 100644
--- a/lib/FCM/Util/Shell.pm
+++ b/lib/FCM/Util/Shell.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM/Util/TaskRunner.pm b/lib/FCM/Util/TaskRunner.pm
index 09cc7cb..0284431 100644
--- a/lib/FCM/Util/TaskRunner.pm
+++ b/lib/FCM/Util/TaskRunner.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/Base.pm b/lib/FCM1/Base.pm
index eb60c97..00718f6 100644
--- a/lib/FCM1/Base.pm
+++ b/lib/FCM1/Base.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/Build.pm b/lib/FCM1/Build.pm
index adb465b..dab89ea 100644
--- a/lib/FCM1/Build.pm
+++ b/lib/FCM1/Build.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/Build/Fortran.pm b/lib/FCM1/Build/Fortran.pm
index 452e32f..69d3c7f 100644
--- a/lib/FCM1/Build/Fortran.pm
+++ b/lib/FCM1/Build/Fortran.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/BuildSrc.pm b/lib/FCM1/BuildSrc.pm
index cd36a52..3dce018 100644
--- a/lib/FCM1/BuildSrc.pm
+++ b/lib/FCM1/BuildSrc.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -407,7 +407,8 @@ sub exebase {
 sub interfacebase {
   my $self = shift();
   if (
-        uc($self->get_setting(qw/TOOL GENINTERFACE/)) ne 'NONE'
+        defined($self->get_setting(qw/TOOL GENINTERFACE/))
+    &&  uc($self->get_setting(qw/TOOL GENINTERFACE/)) ne 'NONE'
     &&  $self->progname()
     &&  $self->is_type_all(qw/SOURCE/)
     &&  $self->is_type_any(qw/FORTRAN9X FPP9X/)
diff --git a/lib/FCM1/BuildTask.pm b/lib/FCM1/BuildTask.pm
index 6b9d0ba..d757f36 100644
--- a/lib/FCM1/BuildTask.pm
+++ b/lib/FCM1/BuildTask.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/CfgFile.pm b/lib/FCM1/CfgFile.pm
index 8f947f8..f1de6c4 100644
--- a/lib/FCM1/CfgFile.pm
+++ b/lib/FCM1/CfgFile.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -241,9 +241,11 @@ sub read_cfg {
       }
     }
 
-    if (exists $exp_inc{uc ($self->type)} and
-        uc ($start ? $start->label : $label) eq $self->cfglabel ('INC') and
-        not defined $cont) {
+    if (    defined($self->type())
+        &&  exists($exp_inc{uc($self->type())})
+        &&  uc($start ? $start->label() : $label) eq $self->cfglabel('INC')
+        &&  !defined($cont)
+    ) {
       # Current configuration file requires expansion of INC declarations
       # The start/current line is an INC declaration
       # The current line is not a continuation or is the end of the continuation
diff --git a/lib/FCM1/CfgLine.pm b/lib/FCM1/CfgLine.pm
index 4819024..10a9c30 100644
--- a/lib/FCM1/CfgLine.pm
+++ b/lib/FCM1/CfgLine.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -217,7 +217,7 @@ for my $name (qw/label slabel/) {
     my @all_fields = $self->$method;
 
     for my $i (0 .. $#fields) {
-      next if lc ($fields[$i]) eq lc ($all_fields[$i]);
+      next if $all_fields[$i] && lc($fields[$i]) eq lc($all_fields[$i]);
       $return = 0;
       last;
     }
diff --git a/lib/FCM1/Cm.pm b/lib/FCM1/Cm.pm
index 6e3c8a6..9ecb26f 100644
--- a/lib/FCM1/Cm.pm
+++ b/lib/FCM1/Cm.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -257,11 +257,11 @@ sub _branch_url {
     my $url
         = $arg && is_url($arg) ? FCM1::CmUrl->new(URL => $arg)
         : $arg && is_wc($arg)  ? FCM1::CmUrl->new(URL => get_url_of_wc($arg))
-        : is_wc()              ? FCM1::CmUrl->new(URL => get_url_of_wc())
+        : !$arg && is_wc()     ? FCM1::CmUrl->new(URL => get_url_of_wc())
         :                        undef
         ;
     if (!$url) {
-        return _cm_err(FCM1::Cm::Exception->INVALID_TARGET, '.');
+        return _cm_err(FCM1::Cm::Exception->INVALID_TARGET, $arg ? $arg : q{.});
     }
     $url;
 }
@@ -351,7 +351,7 @@ sub cm_branch_diff {
             my $browser = $UTIL->external_cfg_get('browser');
             my $trac_url = FCM1::Keyword::get_browser_url($url->project_url());
             # FIXME: assuming that the browser URL uses the InterTrac syntax
-            $trac_url =~ s{/intertrac/.*$}{/intertrac/$wiki_syntax}xms;
+            $trac_url =~ s{/intertrac/.*$}{/search?q=$wiki_syntax}xms;
             my %value_of = %{$UTIL->shell_simple([$browser, $trac_url])};
             if ($value_of{rc}) {
                 return FCM::System::Exception->throw(
@@ -435,7 +435,7 @@ sub cm_commit {
     LINE:
     for my $line (@status) {
       for my $key (keys(%st_lines_of)) {
-        if ($ST_MATCHER_FOR{$key}->($line)) {
+        if ($line && $ST_MATCHER_FOR{$key}->($line)) {
           push(@{$st_lines_of{$key}}, $line);
           next LINE;
         }
@@ -615,9 +615,6 @@ sub cm_merge {
 
   # Parse the revision option
   # ----------------------------------------------------------------------------
-  if ($option_ref->{reverse} && !$option_ref->{revision}) {
-    _cli_err('CLI_OPT_WITH_OPT', 'revision', 'reverse');
-  }
   my @revs
     = (grep {$option_ref->{$_}} qw{reverse custom}) && $option_ref->{revision}
     ? split(qr{:}xms, $option_ref->{revision})
@@ -631,23 +628,29 @@ sub cm_merge {
   if ($option_ref->{reverse}) {
     # Reverse merge
     # --------------------------------------------------------------------------
-    if (@revs == 1) {
+    if (@revs == 0) {
+      my $last_commit_rev = $source->svninfo('FLAG' => 'commit:revision');
+      @revs = ($last_commit_rev, $last_commit_rev - 1);
+    }
+    elsif (@revs == 1) {
       $revs[1] = ($revs[0] - 1);
-
-    } else {
+    }
+    else {
       @revs = sort {$b <=> $a} @revs;
     }
-    $source->url_peg(
-      $source->branch_url() . '/' . $subdir . '@' . $source->pegrev(),
-    );
 
     # "Delta" of the "svn merge" command
     @delta = ('-r' . $revs[0] . ':' . $revs[1], $source->url_peg);
 
     # Template message
-    $mesg = 'Reversed r' . $revs[0] .
-            (($revs[1] < $revs[0] - 1) ? ':' . $revs[1] : '') . ' of ' .
-            $source->path . "\n";
+    $mesg = 'Reversed r' . $revs[0];
+    if ($revs[1] < $revs[0] - 1) {
+      $mesg .= ':' . $revs[1];
+    }
+    if ($source->path()) {
+      $mesg .= ' of ' . $source->path();
+    }
+    $mesg .= "\n";
 
   } elsif ($option_ref->{custom}) {
     # Custom merge
@@ -1812,7 +1815,7 @@ sub _svn_status_get {
         }
     }
     my @options = ($show_updates ? qw{--show-updates} : ());
-    $SVN->stdout(qw{svn status}, @options, @targets);
+    $SVN->stdout(qw{svn status --ignore-externals}, @options, @targets);
 }
 
 # ------------------------------------------------------------------------------
diff --git a/lib/FCM1/CmBranch.pm b/lib/FCM1/CmBranch.pm
index 075d6cf..452fb13 100644
--- a/lib/FCM1/CmBranch.pm
+++ b/lib/FCM1/CmBranch.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/CmUrl.pm b/lib/FCM1/CmUrl.pm
index 67bddc0..ec89b3b 100644
--- a/lib/FCM1/CmUrl.pm
+++ b/lib/FCM1/CmUrl.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/Config.pm b/lib/FCM1/Config.pm
index 35dc3c3..98866cc 100644
--- a/lib/FCM1/Config.pm
+++ b/lib/FCM1/Config.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/ConfigSystem.pm b/lib/FCM1/ConfigSystem.pm
index 144681c..f4aba7b 100644
--- a/lib/FCM1/ConfigSystem.pm
+++ b/lib/FCM1/ConfigSystem.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -606,7 +606,9 @@ sub parse_cfg_dest {
   for my $line (@lines) {
     my ($d, $method) = $line->slabel_fields;
     $d = lc $d;
-    $method = lc $method;
+    if ($method) {
+      $method = lc($method);
+    }
 
     # Backward compatibility
     $d = 'dest' if $d eq 'dir';
diff --git a/lib/FCM1/Dest.pm b/lib/FCM1/Dest.pm
index af65084..a6bbfb0 100644
--- a/lib/FCM1/Dest.pm
+++ b/lib/FCM1/Dest.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/Exception.pm b/lib/FCM1/Exception.pm
index 0b0c192..cdcb05a 100644
--- a/lib/FCM1/Exception.pm
+++ b/lib/FCM1/Exception.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/Extract.pm b/lib/FCM1/Extract.pm
index 9dbda6f..40f8821 100644
--- a/lib/FCM1/Extract.pm
+++ b/lib/FCM1/Extract.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/ExtractConfigComparator.pm b/lib/FCM1/ExtractConfigComparator.pm
index bd4d50c..6606a66 100644
--- a/lib/FCM1/ExtractConfigComparator.pm
+++ b/lib/FCM1/ExtractConfigComparator.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/ExtractFile.pm b/lib/FCM1/ExtractFile.pm
index 309e662..6924c28 100644
--- a/lib/FCM1/ExtractFile.pm
+++ b/lib/FCM1/ExtractFile.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/ExtractSrc.pm b/lib/FCM1/ExtractSrc.pm
index 0cba119..f3332d3 100644
--- a/lib/FCM1/ExtractSrc.pm
+++ b/lib/FCM1/ExtractSrc.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/Interactive.pm b/lib/FCM1/Interactive.pm
index 4339b76..81a9522 100644
--- a/lib/FCM1/Interactive.pm
+++ b/lib/FCM1/Interactive.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/Interactive/InputGetter.pm b/lib/FCM1/Interactive/InputGetter.pm
index 5749133..0b2ab87 100644
--- a/lib/FCM1/Interactive/InputGetter.pm
+++ b/lib/FCM1/Interactive/InputGetter.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/Interactive/InputGetter/CLI.pm b/lib/FCM1/Interactive/InputGetter/CLI.pm
index b28c3af..76ed21e 100644
--- a/lib/FCM1/Interactive/InputGetter/CLI.pm
+++ b/lib/FCM1/Interactive/InputGetter/CLI.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/Interactive/InputGetter/GUI.pm b/lib/FCM1/Interactive/InputGetter/GUI.pm
index f2dfcb9..4fc0e3e 100644
--- a/lib/FCM1/Interactive/InputGetter/GUI.pm
+++ b/lib/FCM1/Interactive/InputGetter/GUI.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/Keyword.pm b/lib/FCM1/Keyword.pm
index 6ed97fc..9360c4e 100644
--- a/lib/FCM1/Keyword.pm
+++ b/lib/FCM1/Keyword.pm
@@ -1,5 +1,5 @@
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/ReposBranch.pm b/lib/FCM1/ReposBranch.pm
index 1194d64..482ed9e 100644
--- a/lib/FCM1/ReposBranch.pm
+++ b/lib/FCM1/ReposBranch.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/SrcDirLayer.pm b/lib/FCM1/SrcDirLayer.pm
index b1dda79..8eac042 100644
--- a/lib/FCM1/SrcDirLayer.pm
+++ b/lib/FCM1/SrcDirLayer.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/Timer.pm b/lib/FCM1/Timer.pm
index 26c080c..93763f2 100644
--- a/lib/FCM1/Timer.pm
+++ b/lib/FCM1/Timer.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/Util.pm b/lib/FCM1/Util.pm
index 2752b11..649cf5d 100644
--- a/lib/FCM1/Util.pm
+++ b/lib/FCM1/Util.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/lib/FCM1/Util/ClassLoader.pm b/lib/FCM1/Util/ClassLoader.pm
index 55a07eb..7f4ad89 100644
--- a/lib/FCM1/Util/ClassLoader.pm
+++ b/lib/FCM1/Util/ClassLoader.pm
@@ -1,5 +1,5 @@
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/man/man1/fcm.1 b/man/man1/fcm.1
index 820e4c4..41cf917 100644
--- a/man/man1/fcm.1
+++ b/man/man1/fcm.1
@@ -23,7 +23,7 @@ Run "fcm help" to access the built-in tool documentation.
 FCM Team <fcm-team at metoffice.gov.uk>.
 Please feedback any bug reports or feature requests to us by e-mail.
 .SH COPYRIGHT
-\(co British Crown Copyright 2006-14 Met Office.
+\(co British Crown Copyright 2006-15 Met Office.
 .PP
 FCM is free software: you can redistribute it and/or modify
 it under the terms of the GNU General Public License as published by
diff --git a/sbin/fcm-add-svn-repos b/sbin/fcm-add-svn-repos
index c4a5c60..881a24b 100755
--- a/sbin/fcm-add-svn-repos
+++ b/sbin/fcm-add-svn-repos
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/fcm-add-svn-repos-and-trac-env b/sbin/fcm-add-svn-repos-and-trac-env
index 8d354c2..5ec3173 100755
--- a/sbin/fcm-add-svn-repos-and-trac-env
+++ b/sbin/fcm-add-svn-repos-and-trac-env
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/fcm-add-trac-env b/sbin/fcm-add-trac-env
index 4b55b08..d7787d9 100755
--- a/sbin/fcm-add-trac-env
+++ b/sbin/fcm-add-trac-env
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/fcm-backup-svn-repos b/sbin/fcm-backup-svn-repos
index 5568c97..8e43f2f 100755
--- a/sbin/fcm-backup-svn-repos
+++ b/sbin/fcm-backup-svn-repos
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/fcm-backup-trac-env b/sbin/fcm-backup-trac-env
index ae1f906..2054570 100755
--- a/sbin/fcm-backup-trac-env
+++ b/sbin/fcm-backup-trac-env
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/fcm-commit-update b/sbin/fcm-commit-update
index 2cd788c..7607d25 100755
--- a/sbin/fcm-commit-update
+++ b/sbin/fcm-commit-update
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/fcm-daily-update b/sbin/fcm-daily-update
index 4b6552e..add9c34 100755
--- a/sbin/fcm-daily-update
+++ b/sbin/fcm-daily-update
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/fcm-install-svn-hook b/sbin/fcm-install-svn-hook
index bc4b07b..820326c 100755
--- a/sbin/fcm-install-svn-hook
+++ b/sbin/fcm-install-svn-hook
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/fcm-manage-trac-env-session b/sbin/fcm-manage-trac-env-session
index 50207cd..6231fa1 100755
--- a/sbin/fcm-manage-trac-env-session
+++ b/sbin/fcm-manage-trac-env-session
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/fcm-manage-users b/sbin/fcm-manage-users
index d7be833..edf3ce5 100755
--- a/sbin/fcm-manage-users
+++ b/sbin/fcm-manage-users
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/fcm-recover-svn-repos b/sbin/fcm-recover-svn-repos
index fa13910..9162fd3 100755
--- a/sbin/fcm-recover-svn-repos
+++ b/sbin/fcm-recover-svn-repos
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/fcm-recover-trac-env b/sbin/fcm-recover-trac-env
index 4d4a7fb..ef49bbd 100755
--- a/sbin/fcm-recover-trac-env
+++ b/sbin/fcm-recover-trac-env
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/fcm-rpmbuild b/sbin/fcm-rpmbuild
index 25c2a27..227308e 100755
--- a/sbin/fcm-rpmbuild
+++ b/sbin/fcm-rpmbuild
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/fcm-user-to-email b/sbin/fcm-user-to-email
index 333198e..8cb55a0 100755
--- a/sbin/fcm-user-to-email
+++ b/sbin/fcm-user-to-email
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/fcm-vacuum-trac-env-db b/sbin/fcm-vacuum-trac-env-db
index eda1546..8143c65 100755
--- a/sbin/fcm-vacuum-trac-env-db
+++ b/sbin/fcm-vacuum-trac-env-db
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/my-regular-update.example b/sbin/my-regular-update.example
index 3aa6c11..6942ce1 100755
--- a/sbin/my-regular-update.example
+++ b/sbin/my-regular-update.example
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/post-commit-bg b/sbin/post-commit-bg
index d71e0e2..8ea5d1c 100755
--- a/sbin/post-commit-bg
+++ b/sbin/post-commit-bg
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -82,9 +82,18 @@ main() {
         fi
         local NAME=$(basename "$REPOS")
         local DUMP="$FCM_SVN_HOOK_COMMIT_DUMP_DIR/$NAME-$REV.gz"
-        echo "svnadmin dump -r$REV --incremental --deltas $REPOS | gzip 1>$DUMP"
-        svnadmin dump "-r$REV" --incremental --deltas "$REPOS" \
-            | gzip 1>"$DUMP" || RET_CODE=$?
+        local TMP_DUMP="$FCM_SVN_HOOK_COMMIT_DUMP_DIR/$NAME-$REV-tmp.gz"
+        echo "svnadmin dump -r$REV --incremental --deltas $REPOS | gzip \\"
+        echo "    | (dd 'conv=fsync' \"of=$TMP_DUMP\" 2>/dev/null)"
+        svnadmin dump "-r$REV" --incremental --deltas "$REPOS" | gzip \
+            | (dd 'conv=fsync' "of=$TMP_DUMP" 2>/dev/null) || RET_CODE=$?
+        if [[ -s "${TMP_DUMP}" ]]; then
+            echo "mv \"${TMP_DUMP}\" \"${DUMP}\""
+            mv "${TMP_DUMP}" "${DUMP}" || RET_CODE=$?
+        else
+            echo "[WARN] ${NAME}-${REV}: zero dump size" >&2
+            rm -f "${TMP_DUMP}"
+        fi
     fi
 
     # Resync Trac
@@ -117,10 +126,10 @@ main() {
         fi
     done
 
-    # On commit to a branch, notify the branch owner if author is not him/her
+    # If relevant, notify owners
     local COMMIT_CONFIG="${REPOS}/hooks/commit.conf"
-    if ! grep -q 'no-notify-branch-owner' "$COMMIT_CONFIG" 2>/dev/null; then
-        local ADDRS=$(post-commit-bg-notify-who "$REPOS" "$REV" "$TXN")
+    if grep -q 'notify-owner' "$COMMIT_CONFIG" 2>/dev/null; then
+        local ADDRS=$('post-commit-bg-notify-who' "$REPOS" "$REV" "$TXN")
         if [[ -n $ADDRS ]]; then
             SUBJECT="-s$(basename $REPOS)@$REV by $AUTHOR"
             FROM=
@@ -129,7 +138,8 @@ main() {
             fi
             echo -n "svn log -v -r \"$REV\" \"file://$REPOS\""
             echo " | mail \"$FROM\" \"$SUBJECT\" \"$ADDRS\""
-            svn log -v -r "$REV" "file://$REPOS" | mail "$FROM" "$SUBJECT" "$ADDRS"
+            svn log -v -r "$REV" "file://$REPOS" \
+                | mail "$FROM" "$SUBJECT" "$ADDRS"
         fi
     fi
 
diff --git a/sbin/post-commit-bg-notify-who b/sbin/post-commit-bg-notify-who
index a557c5b..b93c9bc 100755
--- a/sbin/post-commit-bg-notify-who
+++ b/sbin/post-commit-bg-notify-who
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -26,6 +26,7 @@ use lib "$FindBin::Bin/../lib";
 use FCM::Admin::System qw{get_users};
 use FCM::System::CM::SVN;
 use FCM::Util;
+use Text::ParseWords qw{shellwords};
 
 our @IGNORES = qw{Config Rel Share};
 
@@ -41,28 +42,77 @@ sub main {
     my ($repos, $rev, $txn) = @ARGV;
 
     my %layout_config = $CM_SYS->load_layout_config('file://' . $repos);
-    if (!$layout_config{'level-owner-branch'}) {
+    if (!$layout_config{'level-owner-branch'} && !$layout_config{'owner'}) {
         return;
     }
 
+    my @owners;
+    if (open(my $handle, "$repos/hooks/commit.conf")) {
+        COMMIT_CONF_LINE:
+        while (my $line = readline($handle)) {
+            chomp($line);
+            my ($owners_str) = $line =~ qr{\A\s*owner\s*=\s*(.*)\z}msx;
+            if ($owners_str) {
+                @owners = shellwords($owners_str);
+                last COMMIT_CONF_LINE;
+            }
+        }
+        close($handle);
+    }
+
     my ($author) = $CM_SYS->stdout(qw{svnlook author -r}, $rev, $repos);
 
     # Get list of new paths
+    my %branches = ();  # {$project/$branch1 => 1, $project/$branch2 => 1, ...}
     my %names = (); # {$name1 => 1, $name2 => 1, ...}
     my @lines = $CM_SYS->stdout(qw{svnlook changed -r}, $rev, $repos);
-    LINE:
+    CHANGED_LINE:
     for my $line (@lines) {
         my $status = substr($line, 0, 1);
         my $path = substr($line, 4);
         my $layout = $CM_SYS->get_layout_common(
             $repos,
             ($status eq 'D' ? $rev - 1 : $rev),
-            $path,
+            '/' . $path, # must start with a '/'
             1, # $is_local=1
         );
-        my $owner = $layout->get_branch_owner();
-        if ($owner && $owner ne $author && !grep {$_ eq $owner} @IGNORES) {
-            $names{$owner} = 1;
+        my $project = $layout->get_project();
+        my $branch = $layout->get_branch();
+        if (!$branch || exists($branches{"$project/$branch"})) {
+            next CHANGED_LINE;
+        }
+        $branches{"$project/$branch"} = 1; # so we only do each branch once
+        if (@owners && $layout->is_trunk()) {
+            for my $owner (grep {$_ ne $author} @owners) {
+                $names{$owner} = 1;
+            }
+        }
+        elsif ($layout->is_branch()) {
+            my $owner = $layout->get_branch_owner();
+            if (!$owner || $layout->is_shared()) {
+                # If owner is not in the branch name,
+                # assume owner is branch creator
+                my $url = 'file://' . $layout->get_root();
+                if ($project) {
+                    $url .= '/' . $project;
+                }
+                $url .= '/' . $branch . '@' . $rev;
+                my @lines = $CM_SYS->stdout(
+                    qw{svn log -q --incremental --stop-on-copy --limit 1},
+                    '-r1:' . $rev,
+                    $url,
+                );
+                LOG_LINE:
+                for my $line (reverse(@lines)) {
+                    ($owner) = $line =~ qr{\Ar\d+\s\|\s([^\|]+)\s\|}msx;
+                    if ($owner) {
+                        last LOG_LINE;
+                    }
+                }
+            }
+            if ($owner && $owner ne $author) {
+                $names{$owner} = 1;
+            }
         }
     }
 
diff --git a/sbin/post-revprop-change-bg b/sbin/post-revprop-change-bg
index 0bab5d4..9e804bb 100755
--- a/sbin/post-revprop-change-bg
+++ b/sbin/post-revprop-change-bg
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -68,9 +68,6 @@ main() {
     local NOW=$(date -u +%FT%H:%M:%SZ)
     echo "$NOW+ $ACTION $PROP_NAME @$REV by $PROP_AUTHOR"
 
-    # Resync Trac
-    trac_hook "$REPOS" "$REV" modified || RET_CODE=$?
-
     # Diff old/new in log
     local OLD_FILE=$(mktemp "$REPOS/log/$THIS.$REV.XXXXXXXXXX.old")
     cat >"$OLD_FILE"
@@ -97,6 +94,9 @@ main() {
     fi
     rm -f "$OLD_FILE" "$DIFF_FILE"
 
+    # Resync Trac
+    trac_hook "$REPOS" "$REV" modified || RET_CODE=$?
+
     echo "RET_CODE=$RET_CODE"
     return $RET_CODE
 }
diff --git a/sbin/pre-commit b/sbin/pre-commit
index 00cf366..dc561dc 100755
--- a/sbin/pre-commit
+++ b/sbin/pre-commit
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -85,7 +85,7 @@ main() {
 
     # Verify owner of any new branches, if relevant
     local COMMIT_CONFIG="${REPOS}/hooks/commit.conf"
-    if ! grep -q 'no-verify-branch-owner' "$COMMIT_CONFIG" 2>/dev/null; then
+    if grep -q 'verify-branch-owner' "$COMMIT_CONFIG" 2>/dev/null; then
         pre-commit-verify-branch-owner "$REPOS" "$TXN" || return $?
     fi
 
diff --git a/sbin/pre-commit-verify-branch-owner b/sbin/pre-commit-verify-branch-owner
index 536ec46..06d8d23 100755
--- a/sbin/pre-commit-verify-branch-owner
+++ b/sbin/pre-commit-verify-branch-owner
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/pre-revprop-change b/sbin/pre-revprop-change
index 0c69412..8143b67 100755
--- a/sbin/pre-revprop-change
+++ b/sbin/pre-revprop-change
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/sbin/svnperms.py b/sbin/svnperms.py
index af0eb36..6dc0446 100755
--- a/sbin/svnperms.py
+++ b/sbin/svnperms.py
@@ -25,6 +25,7 @@
 # Original source downloaded from r1295006 at:
 # https://svn.apache.org/viewvc/subversion/trunk/tools/hook-scripts/svnperms.py
 # This version is modified to allow custom permission message per repository.
+# It also fixes the Config.get method.
 
 import sys, os
 import getopt
@@ -111,7 +112,7 @@ class Config:
         return list(self._sections_dict.get(section, {}).keys())
 
     def get(self, section, option, default=None):
-        return self._sections_dict.get(option, default)
+        return self._sections_dict.get(section, {}).get(option, default)
 
     def walk(self, section, option=None):
         ret = []
@@ -267,10 +268,10 @@ def check_perms(filename, section, repos, txn=None, rev=None, author=None):
         #    print "cdata=%s cprop=%s path=%s perms=%s" % \
         #          (str(changedata), str(changeprop), path, str(pathperms))
     if permerrors:
-        message = config.get("message", "permerrors_prefix")
+        message = config.get(" ".join((section, "message")),
+                             "permerrors_prefix")
         if message is None:
-            message = config.get(" ".join((section, "message")),
-                                 "permerrors_prefix")
+            message = config.get("message", "permerrors_prefix")
         if message is None:
             message = "you don't have enough permissions for this transaction:"
         permerrors.insert(0, message)
diff --git a/sbin/trac_hook b/sbin/trac_hook
index 224a1db..a5d2356 100644
--- a/sbin/trac_hook
+++ b/sbin/trac_hook
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-add-trac-env/00-basic.t b/t/fcm-add-trac-env/00-basic.t
index 974f517..72a1b9f 100755
--- a/t/fcm-add-trac-env/00-basic.t
+++ b/t/fcm-add-trac-env/00-basic.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-add/00-simple.t b/t/fcm-add/00-simple.t
index d133099..6d5530b 100644
--- a/t/fcm-add/00-simple.t
+++ b/t/fcm-add/00-simple.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -24,6 +24,7 @@ if [[ $? -ne 0 ]]; then
     exit 1
 fi
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 24
 #-------------------------------------------------------------------------------
 setup
@@ -47,7 +48,9 @@ file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 # Tests fcm add unversioned directory
 TEST_KEY=$TEST_KEY_BASE-fcm-add-dir
 run_pass "$TEST_KEY" fcm add added_directory2
-file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<'__OUT__'
+# Add produces yet another format of status - just use 'sort'...
+sort "$TEST_DIR/$TEST_KEY.out" -o "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<'__OUT__'
 A         added_directory2
 A         added_directory2/added_file2
 __OUT__
@@ -101,8 +104,8 @@ file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 # Tests fcm status after above tests
 TEST_KEY=$TEST_KEY_BASE-fcm-add-c-status
 run_pass "$TEST_KEY" fcm st
-sort $TEST_DIR/"$TEST_KEY.out" -o $TEST_DIR/"$TEST_KEY.out"
-file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<'__OUT__'
+status_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<'__OUT__'
 ?       versioned_directory/unversioned_file_3
 A       unversioned_directory
 A       unversioned_directory/unversioned_file_2
@@ -126,8 +129,8 @@ file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 # Tests fcm status after above tests
 TEST_KEY=$TEST_KEY_BASE-fcm-add-c-no-args-status
 run_pass "$TEST_KEY" fcm status
-sort $TEST_DIR/"$TEST_KEY.out" -o $TEST_DIR/"$TEST_KEY.out"
-file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<'__OUT__'
+status_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<'__OUT__'
 A       unversioned_directory
 A       unversioned_directory/unversioned_file_2
 A       unversioned_file
diff --git a/t/fcm-add/test_header b/t/fcm-add/test_header
index 672ce12..6d52eac 100644
--- a/t/fcm-add/test_header
+++ b/t/fcm-add/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-backup-svn-repos/00-basic.t b/t/fcm-backup-svn-repos/00-basic.t
index bf0651b..7fdeda5 100755
--- a/t/fcm-backup-svn-repos/00-basic.t
+++ b/t/fcm-backup-svn-repos/00-basic.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-branch-create/00-simple.t b/t/fcm-branch-create/00-simple.t
index a6789eb..ece0393 100644
--- a/t/fcm-branch-create/00-simple.t
+++ b/t/fcm-branch-create/00-simple.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 12
 #-------------------------------------------------------------------------------
 setup
diff --git a/t/fcm-branch-create/test_header b/t/fcm-branch-create/test_header
index 672ce12..6d52eac 100644
--- a/t/fcm-branch-create/test_header
+++ b/t/fcm-branch-create/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-branch-delete/00-simple.t b/t/fcm-branch-delete/00-simple.t
index e516af0..0b9cab7 100644
--- a/t/fcm-branch-delete/00-simple.t
+++ b/t/fcm-branch-delete/00-simple.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -17,10 +17,11 @@
 # You should have received a copy of the GNU General Public License
 # along with FCM. If not, see <http://www.gnu.org/licenses/>.
 # ------------------------------------------------------------------------------
-# Basic tests for "fcm branch-create".
+# Basic tests for "fcm branch-delete".
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 12
 #-------------------------------------------------------------------------------
 setup
diff --git a/t/fcm-commit/02-bad.t b/t/fcm-branch-delete/01-bad-arg.t
old mode 100644
new mode 100755
similarity index 57%
copy from t/fcm-commit/02-bad.t
copy to t/fcm-branch-delete/01-bad-arg.t
index 51c85d7..54b5113
--- a/t/fcm-commit/02-bad.t
+++ b/t/fcm-branch-delete/01-bad-arg.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -17,32 +17,24 @@
 # You should have received a copy of the GNU General Public License
 # along with FCM. If not, see <http://www.gnu.org/licenses/>.
 # ------------------------------------------------------------------------------
-# Bad-behaviour tests for "fcm commit".
-#-------------------------------------------------------------------------------
-. $(dirname $0)/test_header
+# Test "fcm branch-delete" with bad argument and in a working copy.
 #-------------------------------------------------------------------------------
+. "$(dirname "$0")/test_header"
 tests 3
 #-------------------------------------------------------------------------------
+# Tests fcm branch-delete with bad argument, and in a working copy
+TEST_KEY="${TEST_KEY_BASE}"
 setup
 init_repos
-init_branch sibling_branch_test $REPOS_URL
-init_branch_wc branch_test $REPOS_URL
-cd $TEST_DIR/wc
-svn copy -q pro/hello.pro copied_file
-svn copy -q module copied_directory
-svn delete -q --force lib
-rm -rf program/hello.F90
-#-------------------------------------------------------------------------------
-# Tests fcm commit
-TEST_KEY=$TEST_KEY_BASE
-export SVN_EDITOR="sed -i 1i\foo" 
-run_fail "$TEST_KEY" fcm commit --svn-non-interactive
-file_cmp "$TEST_KEY.out" "$TEST_KEY.out" </dev/null
-file_cmp "$TEST_KEY.err" "$TEST_KEY.err" <<__ERR__
-[ERROR] File(s) missing:
-!                5   program/hello.F90
-[FAIL] FCM1::Cm::Abort: abort
+init_branch 'branch_test' "${REPOS_URL}"
+init_branch_wc 'my_branch_test' "${REPOS_URL}"
+cd "${TEST_DIR}/wc"
+run_fail "${TEST_KEY}" fcm branch-delete --non-interactive 'dark-matter'
+file_cmp "${TEST_DIR}/${TEST_KEY}.out" "${TEST_KEY}.out" </dev/null
+file_cmp "${TEST_DIR}/${TEST_KEY}.err" "${TEST_KEY}.err" <<'__ERR__'
+[FAIL] dark-matter: not a valid working copy or URL.
 
 __ERR__
 teardown
 #-------------------------------------------------------------------------------
+exit
diff --git a/t/fcm-branch-delete/test_header b/t/fcm-branch-delete/test_header
index 672ce12..6d52eac 100644
--- a/t/fcm-branch-delete/test_header
+++ b/t/fcm-branch-delete/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-branch-diff/00-simple.t b/t/fcm-branch-diff/00-simple.t
index 59d2680..bb1734e 100644
--- a/t/fcm-branch-diff/00-simple.t
+++ b/t/fcm-branch-diff/00-simple.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 18
 #-------------------------------------------------------------------------------
 setup
@@ -52,30 +53,12 @@ svn switch -q $ROOT_URL/branches/dev/Share/branch_test
 # Tests fcm branch-diff
 TEST_KEY=$TEST_KEY_BASE-fcm-branch-diff
 run_pass "$TEST_KEY" fcm branch-diff
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Index: added_file
-===================================================================
---- added_file	(.../$ROOT_URL/trunk)	(revision 0)
-+++ added_file	(revision 6)
-@@ -0,0 +1 @@
-+INCLUDE 'hello_constants.INc'
-Index: added_directory/hello_constants_dummy.inc
-===================================================================
---- added_directory/hello_constants_dummy.inc	(.../$ROOT_URL/trunk)	(revision 0)
-+++ added_directory/hello_constants_dummy.inc	(revision 6)
-@@ -0,0 +1 @@
-+INCLUDE 'hello_constants.INc'
-Index: added_directory/hello_constants.inc
-===================================================================
---- added_directory/hello_constants.inc	(.../$ROOT_URL/trunk)	(revision 0)
-+++ added_directory/hello_constants.inc	(revision 6)
-@@ -0,0 +1,2 @@
-+CHARACTER (
-+LEN=80), PARAMETER :: hello_strINg = 'Hello Earth!!'
+diff_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
+
 Index: added_directory/hello_constants.f90
 ===================================================================
---- added_directory/hello_constants.f90	(.../$ROOT_URL/trunk)	(revision 0)
+--- added_directory/hello_constants.f90	($ROOT_URL/trunk)	(revision 0)
 +++ added_directory/hello_constants.f90	(revision 6)
 @@ -0,0 +1,5 @@
 +MODULE Hello_Constants
@@ -83,31 +66,28 @@ Index: added_directory/hello_constants.f90
 +INCLUDE 'hello_constants_dummy.INc'
 +
 +END MODULE Hello_Constants
-Index: module/hello_constants_dummy.inc
+Index: added_directory/hello_constants.inc
 ===================================================================
---- module/hello_constants_dummy.inc	(.../$ROOT_URL/trunk)	(revision 1)
-+++ module/hello_constants_dummy.inc	(working copy)
-@@ -1 +0,0 @@
--INCLUDE 'hello_constants.inc'
-Index: module/hello_constants.inc
+--- added_directory/hello_constants.inc	($ROOT_URL/trunk)	(revision 0)
++++ added_directory/hello_constants.inc	(revision 6)
+@@ -0,0 +1,2 @@
++CHARACTER (
++LEN=80), PARAMETER :: hello_strINg = 'Hello Earth!!'
+Index: added_directory/hello_constants_dummy.inc
 ===================================================================
---- module/hello_constants.inc	(.../$ROOT_URL/trunk)	(revision 1)
-+++ module/hello_constants.inc	(working copy)
-@@ -1 +0,0 @@
--CHARACTER (LEN=80), PARAMETER :: hello_string = 'Hello Earth!'
-Index: module/hello_constants.f90
+--- added_directory/hello_constants_dummy.inc	($ROOT_URL/trunk)	(revision 0)
++++ added_directory/hello_constants_dummy.inc	(revision 6)
+@@ -0,0 +1 @@
++INCLUDE 'hello_constants.INc'
+Index: added_file
 ===================================================================
---- module/hello_constants.f90	(.../$ROOT_URL/trunk)	(revision 1)
-+++ module/hello_constants.f90	(working copy)
-@@ -1,5 +0,0 @@
--MODULE Hello_Constants
--
--INCLUDE 'hello_constants_dummy.inc'
--
--END MODULE Hello_Constants
+--- added_file	($ROOT_URL/trunk)	(revision 0)
++++ added_file	(revision 6)
+@@ -0,0 +1 @@
++INCLUDE 'hello_constants.INc'
 Index: lib/python/info/poems.py
 ===================================================================
---- lib/python/info/poems.py	(.../$ROOT_URL/trunk)	(revision 1)
+--- lib/python/info/poems.py	($ROOT_URL/trunk)	(revision 1)
 +++ lib/python/info/poems.py	(working copy)
 @@ -1,24 +1,23 @@
 -#!/usr/bin/env python
@@ -143,21 +123,6 @@ Index: lib/python/info/poems.py
  
 -print "\n",  __doc__
 +prINt "\n",  __doc__
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Index: module/hello_constants_dummy.inc
-===================================================================
---- module/hello_constants_dummy.inc	($ROOT_URL/trunk)	(revision 1)
-+++ module/hello_constants_dummy.inc	(working copy)
-@@ -1 +0,0 @@
--INCLUDE 'hello_constants.inc'
-Index: module/hello_constants.inc
-===================================================================
---- module/hello_constants.inc	($ROOT_URL/trunk)	(revision 1)
-+++ module/hello_constants.inc	(working copy)
-@@ -1 +0,0 @@
--CHARACTER (LEN=80), PARAMETER :: hello_string = 'Hello Earth!'
 Index: module/hello_constants.f90
 ===================================================================
 --- module/hello_constants.f90	($ROOT_URL/trunk)	(revision 1)
@@ -168,44 +133,27 @@ Index: module/hello_constants.f90
 -INCLUDE 'hello_constants_dummy.inc'
 -
 -END MODULE Hello_Constants
-Index: lib/python/info/poems.py
+Index: module/hello_constants.inc
 ===================================================================
---- lib/python/info/poems.py	($ROOT_URL/trunk)	(revision 1)
-+++ lib/python/info/poems.py	(working copy)
-@@ -1,24 +1,23 @@
--#!/usr/bin/env python
--# -*- coding: utf-8 -*-
- """The Python, by Hilaire Belloc
- 
- A Python I should not advise,--
--It needs a doctor for its eyes,
-+It needs a doctor FOR its eyes,
- And has the measles yearly.
--However, if you feel inclined
--To get one (to improve your mind,
-+However, if you feel INclINed
-+To get one (
-+to improve your mINd,
- And not from fashion merely),
- Allow no music near its cage;
--And when it flies into a rage
-+And when it flies INto a rage
- Chastise it, most severely.
--I had an aunt in Yucatan
-+I had an aunt IN Yucatan
- Who bought a Python from a man
--And kept it for a pet.
-+And kept it FOR a pet.
- She died, because she never knew
- These simple little rules and few;--
--The Snake is living yet.
-+The Snake is livINg yet.
- """
- 
- import this
- 
--print "\n",  __doc__
-+prINt "\n",  __doc__
+--- module/hello_constants.inc	($ROOT_URL/trunk)	(revision 1)
++++ module/hello_constants.inc	(working copy)
+@@ -1 +0,0 @@
+-CHARACTER (LEN=80), PARAMETER :: hello_string = 'Hello Earth!'
+Index: module/hello_constants_dummy.inc
+===================================================================
+--- module/hello_constants_dummy.inc	($ROOT_URL/trunk)	(revision 1)
++++ module/hello_constants_dummy.inc	(working copy)
+@@ -1 +0,0 @@
+-INCLUDE 'hello_constants.inc'
+__OUT__
+file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
+#-------------------------------------------------------------------------------
+# Tests fcm bdi
+TEST_KEY=$TEST_KEY_BASE-bdi
+run_pass "$TEST_KEY" fcm bdi
+diff_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
+
 Index: added_directory/hello_constants.f90
 ===================================================================
 --- added_directory/hello_constants.f90	($ROOT_URL/trunk)	(revision 0)
@@ -235,69 +183,9 @@ Index: added_file
 +++ added_file	(revision 6)
 @@ -0,0 +1 @@
 +INCLUDE 'hello_constants.INc'
-__OUT__
-fi
-file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
-#-------------------------------------------------------------------------------
-# Tests fcm bdi
-TEST_KEY=$TEST_KEY_BASE-bdi
-run_pass "$TEST_KEY" fcm bdi
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Index: added_file
-===================================================================
---- added_file	(.../$ROOT_URL/trunk)	(revision 0)
-+++ added_file	(revision 6)
-@@ -0,0 +1 @@
-+INCLUDE 'hello_constants.INc'
-Index: added_directory/hello_constants_dummy.inc
-===================================================================
---- added_directory/hello_constants_dummy.inc	(.../$ROOT_URL/trunk)	(revision 0)
-+++ added_directory/hello_constants_dummy.inc	(revision 6)
-@@ -0,0 +1 @@
-+INCLUDE 'hello_constants.INc'
-Index: added_directory/hello_constants.inc
-===================================================================
---- added_directory/hello_constants.inc	(.../$ROOT_URL/trunk)	(revision 0)
-+++ added_directory/hello_constants.inc	(revision 6)
-@@ -0,0 +1,2 @@
-+CHARACTER (
-+LEN=80), PARAMETER :: hello_strINg = 'Hello Earth!!'
-Index: added_directory/hello_constants.f90
-===================================================================
---- added_directory/hello_constants.f90	(.../$ROOT_URL/trunk)	(revision 0)
-+++ added_directory/hello_constants.f90	(revision 6)
-@@ -0,0 +1,5 @@
-+MODULE Hello_Constants
-+
-+INCLUDE 'hello_constants_dummy.INc'
-+
-+END MODULE Hello_Constants
-Index: module/hello_constants_dummy.inc
-===================================================================
---- module/hello_constants_dummy.inc	(.../$ROOT_URL/trunk)	(revision 1)
-+++ module/hello_constants_dummy.inc	(working copy)
-@@ -1 +0,0 @@
--INCLUDE 'hello_constants.inc'
-Index: module/hello_constants.inc
-===================================================================
---- module/hello_constants.inc	(.../$ROOT_URL/trunk)	(revision 1)
-+++ module/hello_constants.inc	(working copy)
-@@ -1 +0,0 @@
--CHARACTER (LEN=80), PARAMETER :: hello_string = 'Hello Earth!'
-Index: module/hello_constants.f90
-===================================================================
---- module/hello_constants.f90	(.../$ROOT_URL/trunk)	(revision 1)
-+++ module/hello_constants.f90	(working copy)
-@@ -1,5 +0,0 @@
--MODULE Hello_Constants
--
--INCLUDE 'hello_constants_dummy.inc'
--
--END MODULE Hello_Constants
 Index: lib/python/info/poems.py
 ===================================================================
---- lib/python/info/poems.py	(.../$ROOT_URL/trunk)	(revision 1)
+--- lib/python/info/poems.py	($ROOT_URL/trunk)	(revision 1)
 +++ lib/python/info/poems.py	(working copy)
 @@ -1,24 +1,23 @@
 -#!/usr/bin/env python
@@ -333,21 +221,6 @@ Index: lib/python/info/poems.py
  
 -print "\n",  __doc__
 +prINt "\n",  __doc__
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Index: module/hello_constants_dummy.inc
-===================================================================
---- module/hello_constants_dummy.inc	($ROOT_URL/trunk)	(revision 1)
-+++ module/hello_constants_dummy.inc	(working copy)
-@@ -1 +0,0 @@
--INCLUDE 'hello_constants.inc'
-Index: module/hello_constants.inc
-===================================================================
---- module/hello_constants.inc	($ROOT_URL/trunk)	(revision 1)
-+++ module/hello_constants.inc	(working copy)
-@@ -1 +0,0 @@
--CHARACTER (LEN=80), PARAMETER :: hello_string = 'Hello Earth!'
 Index: module/hello_constants.f90
 ===================================================================
 --- module/hello_constants.f90	($ROOT_URL/trunk)	(revision 1)
@@ -358,75 +231,19 @@ Index: module/hello_constants.f90
 -INCLUDE 'hello_constants_dummy.inc'
 -
 -END MODULE Hello_Constants
-Index: lib/python/info/poems.py
-===================================================================
---- lib/python/info/poems.py	($ROOT_URL/trunk)	(revision 1)
-+++ lib/python/info/poems.py	(working copy)
-@@ -1,24 +1,23 @@
--#!/usr/bin/env python
--# -*- coding: utf-8 -*-
- """The Python, by Hilaire Belloc
- 
- A Python I should not advise,--
--It needs a doctor for its eyes,
-+It needs a doctor FOR its eyes,
- And has the measles yearly.
--However, if you feel inclined
--To get one (to improve your mind,
-+However, if you feel INclINed
-+To get one (
-+to improve your mINd,
- And not from fashion merely),
- Allow no music near its cage;
--And when it flies into a rage
-+And when it flies INto a rage
- Chastise it, most severely.
--I had an aunt in Yucatan
-+I had an aunt IN Yucatan
- Who bought a Python from a man
--And kept it for a pet.
-+And kept it FOR a pet.
- She died, because she never knew
- These simple little rules and few;--
--The Snake is living yet.
-+The Snake is livINg yet.
- """
- 
- import this
- 
--print "\n",  __doc__
-+prINt "\n",  __doc__
-Index: added_directory/hello_constants.f90
-===================================================================
---- added_directory/hello_constants.f90	($ROOT_URL/trunk)	(revision 0)
-+++ added_directory/hello_constants.f90	(revision 6)
-@@ -0,0 +1,5 @@
-+MODULE Hello_Constants
-+
-+INCLUDE 'hello_constants_dummy.INc'
-+
-+END MODULE Hello_Constants
-Index: added_directory/hello_constants.inc
-===================================================================
---- added_directory/hello_constants.inc	($ROOT_URL/trunk)	(revision 0)
-+++ added_directory/hello_constants.inc	(revision 6)
-@@ -0,0 +1,2 @@
-+CHARACTER (
-+LEN=80), PARAMETER :: hello_strINg = 'Hello Earth!!'
-Index: added_directory/hello_constants_dummy.inc
+Index: module/hello_constants.inc
 ===================================================================
---- added_directory/hello_constants_dummy.inc	($ROOT_URL/trunk)	(revision 0)
-+++ added_directory/hello_constants_dummy.inc	(revision 6)
-@@ -0,0 +1 @@
-+INCLUDE 'hello_constants.INc'
-Index: added_file
+--- module/hello_constants.inc	($ROOT_URL/trunk)	(revision 1)
++++ module/hello_constants.inc	(working copy)
+@@ -1 +0,0 @@
+-CHARACTER (LEN=80), PARAMETER :: hello_string = 'Hello Earth!'
+Index: module/hello_constants_dummy.inc
 ===================================================================
---- added_file	($ROOT_URL/trunk)	(revision 0)
-+++ added_file	(revision 6)
-@@ -0,0 +1 @@
-+INCLUDE 'hello_constants.INc'
+--- module/hello_constants_dummy.inc	($ROOT_URL/trunk)	(revision 1)
++++ module/hello_constants_dummy.inc	(working copy)
+@@ -1 +0,0 @@
+-INCLUDE 'hello_constants.inc'
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests fcm branch-diff --wiki
@@ -462,36 +279,18 @@ echo "foo" > added_directory/foo$TEST_KEY
 svn add -q added_directory/foo$TEST_KEY
 echo "bar" > added_directory/bar$TEST_KEY
 run_pass "$TEST_KEY" fcm bdi
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Index: added_file
-===================================================================
---- added_file	(.../$ROOT_URL/trunk)	(revision 0)
-+++ added_file	(revision 6)
-@@ -0,0 +1 @@
-+INCLUDE 'hello_constants.INc'
-Index: added_directory/hello_constants_dummy.inc
-===================================================================
---- added_directory/hello_constants_dummy.inc	(.../$ROOT_URL/trunk)	(revision 0)
-+++ added_directory/hello_constants_dummy.inc	(revision 6)
-@@ -0,0 +1 @@
-+INCLUDE 'hello_constants.INc'
+diff_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
+
 Index: added_directory/foo00-simple-bdi-wc-changes
 ===================================================================
---- added_directory/foo00-simple-bdi-wc-changes	(.../$ROOT_URL/trunk)	(revision 0)
-+++ added_directory/foo00-simple-bdi-wc-changes	(revision 0)
+--- added_directory/foo00-simple-bdi-wc-changes	($ROOT_URL/trunk)	(revision 0)
++++ added_directory/foo00-simple-bdi-wc-changes	(working copy)
 @@ -0,0 +1 @@
 +foo
-Index: added_directory/hello_constants.inc
-===================================================================
---- added_directory/hello_constants.inc	(.../$ROOT_URL/trunk)	(revision 0)
-+++ added_directory/hello_constants.inc	(revision 6)
-@@ -0,0 +1,2 @@
-+CHARACTER (
-+LEN=80), PARAMETER :: hello_strINg = 'Hello Earth!!'
 Index: added_directory/hello_constants.f90
 ===================================================================
---- added_directory/hello_constants.f90	(.../$ROOT_URL/trunk)	(revision 0)
+--- added_directory/hello_constants.f90	($ROOT_URL/trunk)	(revision 0)
 +++ added_directory/hello_constants.f90	(revision 6)
 @@ -0,0 +1,5 @@
 +MODULE Hello_Constants
@@ -499,31 +298,28 @@ Index: added_directory/hello_constants.f90
 +INCLUDE 'hello_constants_dummy.INc'
 +
 +END MODULE Hello_Constants
-Index: module/hello_constants_dummy.inc
+Index: added_directory/hello_constants.inc
 ===================================================================
---- module/hello_constants_dummy.inc	(.../$ROOT_URL/trunk)	(revision 1)
-+++ module/hello_constants_dummy.inc	(working copy)
-@@ -1 +0,0 @@
--INCLUDE 'hello_constants.inc'
-Index: module/hello_constants.inc
+--- added_directory/hello_constants.inc	($ROOT_URL/trunk)	(revision 0)
++++ added_directory/hello_constants.inc	(revision 6)
+@@ -0,0 +1,2 @@
++CHARACTER (
++LEN=80), PARAMETER :: hello_strINg = 'Hello Earth!!'
+Index: added_directory/hello_constants_dummy.inc
 ===================================================================
---- module/hello_constants.inc	(.../$ROOT_URL/trunk)	(revision 1)
-+++ module/hello_constants.inc	(working copy)
-@@ -1 +0,0 @@
--CHARACTER (LEN=80), PARAMETER :: hello_string = 'Hello Earth!'
-Index: module/hello_constants.f90
+--- added_directory/hello_constants_dummy.inc	($ROOT_URL/trunk)	(revision 0)
++++ added_directory/hello_constants_dummy.inc	(revision 6)
+@@ -0,0 +1 @@
++INCLUDE 'hello_constants.INc'
+Index: added_file
 ===================================================================
---- module/hello_constants.f90	(.../$ROOT_URL/trunk)	(revision 1)
-+++ module/hello_constants.f90	(working copy)
-@@ -1,5 +0,0 @@
--MODULE Hello_Constants
--
--INCLUDE 'hello_constants_dummy.inc'
--
--END MODULE Hello_Constants
+--- added_file	($ROOT_URL/trunk)	(revision 0)
++++ added_file	(revision 6)
+@@ -0,0 +1 @@
++INCLUDE 'hello_constants.INc'
 Index: lib/python/info/poems.py
 ===================================================================
---- lib/python/info/poems.py	(.../$ROOT_URL/trunk)	(revision 1)
+--- lib/python/info/poems.py	($ROOT_URL/trunk)	(revision 1)
 +++ lib/python/info/poems.py	(working copy)
 @@ -1,24 +1,23 @@
 -#!/usr/bin/env python
@@ -559,21 +355,6 @@ Index: lib/python/info/poems.py
  
 -print "\n",  __doc__
 +prINt "\n",  __doc__
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Index: module/hello_constants_dummy.inc
-===================================================================
---- module/hello_constants_dummy.inc	($ROOT_URL/trunk)	(revision 1)
-+++ module/hello_constants_dummy.inc	(working copy)
-@@ -1 +0,0 @@
--INCLUDE 'hello_constants.inc'
-Index: module/hello_constants.inc
-===================================================================
---- module/hello_constants.inc	($ROOT_URL/trunk)	(revision 1)
-+++ module/hello_constants.inc	(working copy)
-@@ -1 +0,0 @@
--CHARACTER (LEN=80), PARAMETER :: hello_string = 'Hello Earth!'
 Index: module/hello_constants.f90
 ===================================================================
 --- module/hello_constants.f90	($ROOT_URL/trunk)	(revision 1)
@@ -584,81 +365,19 @@ Index: module/hello_constants.f90
 -INCLUDE 'hello_constants_dummy.inc'
 -
 -END MODULE Hello_Constants
-Index: lib/python/info/poems.py
-===================================================================
---- lib/python/info/poems.py	($ROOT_URL/trunk)	(revision 1)
-+++ lib/python/info/poems.py	(working copy)
-@@ -1,24 +1,23 @@
--#!/usr/bin/env python
--# -*- coding: utf-8 -*-
- """The Python, by Hilaire Belloc
- 
- A Python I should not advise,--
--It needs a doctor for its eyes,
-+It needs a doctor FOR its eyes,
- And has the measles yearly.
--However, if you feel inclined
--To get one (to improve your mind,
-+However, if you feel INclINed
-+To get one (
-+to improve your mINd,
- And not from fashion merely),
- Allow no music near its cage;
--And when it flies into a rage
-+And when it flies INto a rage
- Chastise it, most severely.
--I had an aunt in Yucatan
-+I had an aunt IN Yucatan
- Who bought a Python from a man
--And kept it for a pet.
-+And kept it FOR a pet.
- She died, because she never knew
- These simple little rules and few;--
--The Snake is living yet.
-+The Snake is livINg yet.
- """
- 
- import this
- 
--print "\n",  __doc__
-+prINt "\n",  __doc__
-Index: added_directory/foo00-simple-bdi-wc-changes
-===================================================================
---- added_directory/foo00-simple-bdi-wc-changes	($ROOT_URL/trunk)	(revision 0)
-+++ added_directory/foo00-simple-bdi-wc-changes	(working copy)
-@@ -0,0 +1 @@
-+foo
-Index: added_directory/hello_constants.f90
-===================================================================
---- added_directory/hello_constants.f90	($ROOT_URL/trunk)	(revision 0)
-+++ added_directory/hello_constants.f90	(revision 6)
-@@ -0,0 +1,5 @@
-+MODULE Hello_Constants
-+
-+INCLUDE 'hello_constants_dummy.INc'
-+
-+END MODULE Hello_Constants
-Index: added_directory/hello_constants.inc
-===================================================================
---- added_directory/hello_constants.inc	($ROOT_URL/trunk)	(revision 0)
-+++ added_directory/hello_constants.inc	(revision 6)
-@@ -0,0 +1,2 @@
-+CHARACTER (
-+LEN=80), PARAMETER :: hello_strINg = 'Hello Earth!!'
-Index: added_directory/hello_constants_dummy.inc
+Index: module/hello_constants.inc
 ===================================================================
---- added_directory/hello_constants_dummy.inc	($ROOT_URL/trunk)	(revision 0)
-+++ added_directory/hello_constants_dummy.inc	(revision 6)
-@@ -0,0 +1 @@
-+INCLUDE 'hello_constants.INc'
-Index: added_file
+--- module/hello_constants.inc	($ROOT_URL/trunk)	(revision 1)
++++ module/hello_constants.inc	(working copy)
+@@ -1 +0,0 @@
+-CHARACTER (LEN=80), PARAMETER :: hello_string = 'Hello Earth!'
+Index: module/hello_constants_dummy.inc
 ===================================================================
---- added_file	($ROOT_URL/trunk)	(revision 0)
-+++ added_file	(revision 6)
-@@ -0,0 +1 @@
-+INCLUDE 'hello_constants.INc'
+--- module/hello_constants_dummy.inc	($ROOT_URL/trunk)	(revision 1)
++++ module/hello_constants_dummy.inc	(working copy)
+@@ -1 +0,0 @@
+-INCLUDE 'hello_constants.inc'
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 teardown
 #-------------------------------------------------------------------------------
diff --git a/t/fcm-branch-diff/test_header b/t/fcm-branch-diff/test_header
index 672ce12..6d52eac 100644
--- a/t/fcm-branch-diff/test_header
+++ b/t/fcm-branch-diff/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-branch-info/00-simple.t b/t/fcm-branch-info/00-simple.t
index 338a002..c604d0e 100644
--- a/t/fcm-branch-info/00-simple.t
+++ b/t/fcm-branch-info/00-simple.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 12
 #-------------------------------------------------------------------------------
 setup
diff --git a/t/fcm-branch-info/test_header b/t/fcm-branch-info/test_header
index 672ce12..6d52eac 100644
--- a/t/fcm-branch-info/test_header
+++ b/t/fcm-branch-info/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-branch-list/00-simple.t b/t/fcm-branch-list/00-simple.t
index 8c5c68e..a3fd25c 100644
--- a/t/fcm-branch-list/00-simple.t
+++ b/t/fcm-branch-list/00-simple.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 23
 #-------------------------------------------------------------------------------
 setup
diff --git a/t/fcm-branch-list/test_header b/t/fcm-branch-list/test_header
index 672ce12..6d52eac 100644
--- a/t/fcm-branch-list/test_header
+++ b/t/fcm-branch-list/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/27-args-only.t b/t/fcm-build/00-geninterface.t
similarity index 63%
copy from t/fcm-make/27-args-only.t
copy to t/fcm-build/00-geninterface.t
index 59feaa4..36fdb24 100755
--- a/t/fcm-make/27-args-only.t
+++ b/t/fcm-build/00-geninterface.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -17,25 +17,36 @@
 # You should have received a copy of the GNU General Public License
 # along with FCM. If not, see <http://www.gnu.org/licenses/>.
 #-------------------------------------------------------------------------------
-# Tests "fcm make", no configuration files, only CLI arguments.
+# #156 breaks interface generation. This test ensures that it is not broken
+# again.
 #-------------------------------------------------------------------------------
-. $(dirname $0)/test_header
+. "$(dirname "$0")/test_header"
+tests 2
 #-------------------------------------------------------------------------------
-tests 3
+
+cat >'bld.cfg' <<'__FCM_BLD_CFG__'
+cfg::type bld
+dest $HERE
+tool::geninterface
+__FCM_BLD_CFG__
+
+mkdir 'src'
+cat >'src/hello.f90' <<'__FORTRAN__'
+subroutine hello(world)
+character(*), intent(in) :: world
+write(*, '(a)') 'Hello ' // trim(world)
+end subroutine hello
+__FORTRAN__
+
 #-------------------------------------------------------------------------------
-TEST_KEY="$TEST_KEY_BASE"
-mkdir src
-cat >src/hello.f90 <<'__FORTRAN__'
-program hello
-write(*, '(a)') 'Hello World!'
-end program hello
+run_pass "${TEST_KEY_BASE}-cmd" fcm build -f -s 4
+file_cmp "${TEST_KEY_BASE}-interface" 'inc/hello.interface' <<'__FORTRAN__'
+interface
+subroutine hello(world)
+character(*), intent(in) :: world
+end subroutine hello
+end interface
 __FORTRAN__
-run_pass "$TEST_KEY" fcm make \
-    'steps=build' "build.source=$PWD/src" 'build.target=hello.exe'
-file_test "$TEST_KEY.hello.exe" $PWD/build/bin/hello.exe
-$PWD/build/bin/hello.exe >"$TEST_KEY.hello.exe.out"
-file_cmp "$TEST_KEY.hello.exe.out" "$TEST_KEY.hello.exe.out" <<'__OUT__'
-Hello World!
-__OUT__
+
 #-------------------------------------------------------------------------------
-exit 0
+exit
diff --git a/t/fcm-build/test_header b/t/fcm-build/test_header
new file mode 120000
index 0000000..90bd5a3
--- /dev/null
+++ b/t/fcm-build/test_header
@@ -0,0 +1 @@
+../lib/bash/test_header
\ No newline at end of file
diff --git a/t/fcm-commit/00-simple.t b/t/fcm-commit/00-simple.t
index 5033679..4e49ac1 100644
--- a/t/fcm-commit/00-simple.t
+++ b/t/fcm-commit/00-simple.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 3
 #-------------------------------------------------------------------------------
 setup
@@ -45,8 +46,8 @@ export SVN_EDITOR="sed -i 1i\foo"
 run_pass "$TEST_KEY" fcm commit --svn-non-interactive <<__IN__
 y
 __IN__
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+commit_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
 [info] sed -i 1i\foo: starting commit message editor...
 Change summary:
 --------------------------------------------------------------------------------
@@ -55,57 +56,16 @@ Change summary:
 [Branch : branches/dev/Share/branch_test]
 [Sub-dir: ]
 
+A  +    added_directory
 A  +    added_file
 D       module
-D       module/hello_constants_dummy.inc
-D       module/hello_constants.inc
 D       module/hello_constants.f90
-A  +    added_directory
-M  +    added_directory/hello_constants_dummy.inc
-M  +    added_directory/hello_constants.inc
-M  +    added_directory/hello_constants.f90
+D       module/hello_constants.inc
+D       module/hello_constants_dummy.inc
 M       lib/python/info/poems.py
---------------------------------------------------------------------------------
-Commit message is as follows:
---------------------------------------------------------------------------------
-foo
---------------------------------------------------------------------------------
-
-*** WARNING: YOU ARE COMMITTING TO A Share BRANCH.
-*** Please ensure that you have the owner's permission.
-
-Would you like to commit this change?
-Enter "y" or "n" (or just press <return> for "n"): Adding         added_directory
-Sending        added_directory/hello_constants.f90
-Sending        added_directory/hello_constants.inc
-Sending        added_directory/hello_constants_dummy.inc
-Adding         added_file
-Sending        lib/python/info/poems.py
-Deleting       module
-Transmitting file data .....
-Committed revision 6.
-At revision 6.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-[info] sed -i 1i\foo: starting commit message editor...
-Change summary:
---------------------------------------------------------------------------------
-[Root   : $REPOS_URL]
-[Project: ${TEST_PROJECT:-}]
-[Branch : branches/dev/Share/branch_test]
-[Sub-dir: ]
-
-A  +    added_directory
 M  +    added_directory/hello_constants.f90
 M  +    added_directory/hello_constants.inc
 M  +    added_directory/hello_constants_dummy.inc
-A  +    added_file
-M       lib/python/info/poems.py
-D       module
-D       module/hello_constants.f90
-D       module/hello_constants.inc
-D       module/hello_constants_dummy.inc
 --------------------------------------------------------------------------------
 Commit message is as follows:
 --------------------------------------------------------------------------------
@@ -117,18 +77,17 @@ foo
 
 Would you like to commit this change?
 Enter "y" or "n" (or just press <return> for "n"): Adding         added_directory
+Adding         added_file
+Deleting       module
 Sending        added_directory/hello_constants.f90
 Sending        added_directory/hello_constants.inc
 Sending        added_directory/hello_constants_dummy.inc
-Adding         added_file
 Sending        lib/python/info/poems.py
-Deleting       module
 Transmitting file data .....
 Committed revision 6.
 Updating '.':
 At revision 6.
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 teardown
 #-------------------------------------------------------------------------------
diff --git a/t/fcm-commit/01-subtree.t b/t/fcm-commit/01-subtree.t
index b651608..7c3cd56 100644
--- a/t/fcm-commit/01-subtree.t
+++ b/t/fcm-commit/01-subtree.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 3
 #-------------------------------------------------------------------------------
 setup
@@ -46,8 +47,8 @@ cd program
 run_pass "$TEST_KEY" fcm commit --svn-non-interactive <<__IN__
 y
 __IN__
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+commit_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
 $TEST_DIR/wc: working directory changed to top of working copy.
 [info] sed -i 1i\foo: starting commit message editor...
 Change summary:
@@ -57,58 +58,16 @@ Change summary:
 [Branch : branches/dev/Share/branch_test]
 [Sub-dir: ]
 
+A  +    added_directory
 A  +    added_file
 D       module
-D       module/hello_constants_dummy.inc
-D       module/hello_constants.inc
 D       module/hello_constants.f90
-A  +    added_directory
-M  +    added_directory/hello_constants_dummy.inc
-M  +    added_directory/hello_constants.inc
-M  +    added_directory/hello_constants.f90
+D       module/hello_constants.inc
+D       module/hello_constants_dummy.inc
 M       lib/python/info/poems.py
---------------------------------------------------------------------------------
-Commit message is as follows:
---------------------------------------------------------------------------------
-foo
---------------------------------------------------------------------------------
-
-*** WARNING: YOU ARE COMMITTING TO A Share BRANCH.
-*** Please ensure that you have the owner's permission.
-
-Would you like to commit this change?
-Enter "y" or "n" (or just press <return> for "n"): Adding         added_directory
-Sending        added_directory/hello_constants.f90
-Sending        added_directory/hello_constants.inc
-Sending        added_directory/hello_constants_dummy.inc
-Adding         added_file
-Sending        lib/python/info/poems.py
-Deleting       module
-Transmitting file data .....
-Committed revision 6.
-At revision 6.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-$TEST_DIR/wc: working directory changed to top of working copy.
-[info] sed -i 1i\foo: starting commit message editor...
-Change summary:
---------------------------------------------------------------------------------
-[Root   : $REPOS_URL]
-[Project: ${TEST_PROJECT:-}]
-[Branch : branches/dev/Share/branch_test]
-[Sub-dir: ]
-
-A  +    added_directory
 M  +    added_directory/hello_constants.f90
 M  +    added_directory/hello_constants.inc
 M  +    added_directory/hello_constants_dummy.inc
-A  +    added_file
-M       lib/python/info/poems.py
-D       module
-D       module/hello_constants.f90
-D       module/hello_constants.inc
-D       module/hello_constants_dummy.inc
 --------------------------------------------------------------------------------
 Commit message is as follows:
 --------------------------------------------------------------------------------
@@ -120,18 +79,17 @@ foo
 
 Would you like to commit this change?
 Enter "y" or "n" (or just press <return> for "n"): Adding         added_directory
+Adding         added_file
+Deleting       module
 Sending        added_directory/hello_constants.f90
 Sending        added_directory/hello_constants.inc
 Sending        added_directory/hello_constants_dummy.inc
-Adding         added_file
 Sending        lib/python/info/poems.py
-Deleting       module
 Transmitting file data .....
 Committed revision 6.
 Updating '.':
 At revision 6.
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 teardown
 #-------------------------------------------------------------------------------
diff --git a/t/fcm-commit/02-bad.t b/t/fcm-commit/02-bad.t
index 51c85d7..33976ef 100644
--- a/t/fcm-commit/02-bad.t
+++ b/t/fcm-commit/02-bad.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 3
 #-------------------------------------------------------------------------------
 setup
diff --git a/t/fcm-commit/03-message-file.t b/t/fcm-commit/03-message-file.t
index 12de033..1845a89 100644
--- a/t/fcm-commit/03-message-file.t
+++ b/t/fcm-commit/03-message-file.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 6
 #-------------------------------------------------------------------------------
 svnadmin create foo
diff --git a/t/fcm-commit/02-bad.t b/t/fcm-commit/04-externals.t
old mode 100644
new mode 100755
similarity index 63%
copy from t/fcm-commit/02-bad.t
copy to t/fcm-commit/04-externals.t
index 51c85d7..c08a8d8
--- a/t/fcm-commit/02-bad.t
+++ b/t/fcm-commit/04-externals.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -17,32 +17,25 @@
 # You should have received a copy of the GNU General Public License
 # along with FCM. If not, see <http://www.gnu.org/licenses/>.
 # ------------------------------------------------------------------------------
-# Bad-behaviour tests for "fcm commit".
+# Tests for "fcm commit", in a working copy with externals.
 #-------------------------------------------------------------------------------
-. $(dirname $0)/test_header
+. "$(dirname "$0")/test_header"
 #-------------------------------------------------------------------------------
-tests 3
+check_svn_version
+tests 2
 #-------------------------------------------------------------------------------
-setup
-init_repos
-init_branch sibling_branch_test $REPOS_URL
-init_branch_wc branch_test $REPOS_URL
-cd $TEST_DIR/wc
-svn copy -q pro/hello.pro copied_file
-svn copy -q module copied_directory
-svn delete -q --force lib
-rm -rf program/hello.F90
+svnadmin create 'foo'
+svnadmin create 'bar'
+svn co -q "file://${PWD}/foo" 'test-work'
+svn ps svn:externals "test-work/bar file://${PWD}/bar" 'test-work'
+svn ci -q -m 'set external' 'test-work'
+svn update 'test-work'
+echo 'Whatever!' >'test-work/whatever.txt'
+svn add 'test-work/whatever.txt'
+export SVN_EDITOR="sed -i 1i\foo"
 #-------------------------------------------------------------------------------
-# Tests fcm commit
-TEST_KEY=$TEST_KEY_BASE
-export SVN_EDITOR="sed -i 1i\foo" 
-run_fail "$TEST_KEY" fcm commit --svn-non-interactive
-file_cmp "$TEST_KEY.out" "$TEST_KEY.out" </dev/null
-file_cmp "$TEST_KEY.err" "$TEST_KEY.err" <<__ERR__
-[ERROR] File(s) missing:
-!                5   program/hello.F90
-[FAIL] FCM1::Cm::Abort: abort
-
-__ERR__
-teardown
+TEST_KEY="${TEST_KEY_BASE}"
+run_pass "${TEST_KEY}" fcm commit --svn-non-interactive 'test-work' <<<'y'
+file_cmp "${TEST_KEY}.err" "${TEST_KEY}.err" <'/dev/null'
 #-------------------------------------------------------------------------------
+exit
diff --git a/t/fcm-commit/test_header b/t/fcm-commit/test_header
index 672ce12..6d52eac 100644
--- a/t/fcm-commit/test_header
+++ b/t/fcm-commit/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-conflicts/00-tree-add-add.t b/t/fcm-conflicts/00-tree-add-add.t
index ea1207f..e746d22 100644
--- a/t/fcm-conflicts/00-tree-add-add.t
+++ b/t/fcm-conflicts/00-tree-add-add.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 24
 #-------------------------------------------------------------------------------
 setup
diff --git a/t/fcm-conflicts/01-tree-delete-delete.t b/t/fcm-conflicts/01-tree-delete-delete.t
index 57140c6..ce6ab99 100644
--- a/t/fcm-conflicts/01-tree-delete-delete.t
+++ b/t/fcm-conflicts/01-tree-delete-delete.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 12
 #-------------------------------------------------------------------------------
 setup
diff --git a/t/fcm-conflicts/02-tree-delete-edit.t b/t/fcm-conflicts/02-tree-delete-edit.t
index 02f71ce..eb6a2d8 100644
--- a/t/fcm-conflicts/02-tree-delete-edit.t
+++ b/t/fcm-conflicts/02-tree-delete-edit.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 18
 #-------------------------------------------------------------------------------
 setup
diff --git a/t/fcm-conflicts/03-tree-delete-rename.t b/t/fcm-conflicts/03-tree-delete-rename.t
index 56b4bfd..3ff4116 100644
--- a/t/fcm-conflicts/03-tree-delete-rename.t
+++ b/t/fcm-conflicts/03-tree-delete-rename.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 15
 #-------------------------------------------------------------------------------
 setup
diff --git a/t/fcm-conflicts/04-tree-edit-delete.t b/t/fcm-conflicts/04-tree-edit-delete.t
index a1ac908..51c023d 100644
--- a/t/fcm-conflicts/04-tree-edit-delete.t
+++ b/t/fcm-conflicts/04-tree-edit-delete.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 18
 #-------------------------------------------------------------------------------
 setup
diff --git a/t/fcm-conflicts/05-tree-edit-rename.t b/t/fcm-conflicts/05-tree-edit-rename.t
index 7e2fc01..bac7eb6 100644
--- a/t/fcm-conflicts/05-tree-edit-rename.t
+++ b/t/fcm-conflicts/05-tree-edit-rename.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 24
 #-------------------------------------------------------------------------------
 setup
diff --git a/t/fcm-conflicts/06-tree-rename-delete.t b/t/fcm-conflicts/06-tree-rename-delete.t
index be05fbb..7dafc6f 100644
--- a/t/fcm-conflicts/06-tree-rename-delete.t
+++ b/t/fcm-conflicts/06-tree-rename-delete.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 15
 #-------------------------------------------------------------------------------
 setup
diff --git a/t/fcm-conflicts/07-tree-rename-edit.t b/t/fcm-conflicts/07-tree-rename-edit.t
index 28d74ea..f73aefc 100644
--- a/t/fcm-conflicts/07-tree-rename-edit.t
+++ b/t/fcm-conflicts/07-tree-rename-edit.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 18
 #-------------------------------------------------------------------------------
 setup
diff --git a/t/fcm-conflicts/08-tree-rename-rename-diff.t b/t/fcm-conflicts/08-tree-rename-rename-diff.t
index fd44a7a..11ccc00 100644
--- a/t/fcm-conflicts/08-tree-rename-rename-diff.t
+++ b/t/fcm-conflicts/08-tree-rename-rename-diff.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 18
 #-------------------------------------------------------------------------------
 setup
diff --git a/t/fcm-conflicts/09-tree-rename-rename-same.t b/t/fcm-conflicts/09-tree-rename-rename-same.t
index 4fb2d91..c257cb1 100644
--- a/t/fcm-conflicts/09-tree-rename-rename-same.t
+++ b/t/fcm-conflicts/09-tree-rename-rename-same.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -22,6 +22,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 33
 #-------------------------------------------------------------------------------
 setup
diff --git a/t/fcm-conflicts/10-text.t b/t/fcm-conflicts/10-text.t
index de7c53f..29eac16 100644
--- a/t/fcm-conflicts/10-text.t
+++ b/t/fcm-conflicts/10-text.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 11
 #-------------------------------------------------------------------------------
 setup
@@ -38,44 +39,24 @@ file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 TEST_KEY=$TEST_KEY_BASE-merge-status
 run_pass "$TEST_KEY" svn status --config-dir=$TEST_DIR/.subversion/
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<'__OUT__'
+status_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<'__OUT__'
  M      .
-?       unversioned_file
-M       subroutine/hello_sub_dummy.h
-A  +    added_file
-A  +    module/tree_conflict_file
-M       module/hello_constants_dummy.inc
-M       module/hello_constants.inc
-M       module/hello_constants.f90
-A  +    added_directory
-A  +    added_directory/hello_constants_dummy.inc
-A  +    added_directory/hello_constants.inc
-A  +    added_directory/hello_constants.f90
 ?       lib/python/info/poems.py.merge-left.r1
 ?       lib/python/info/poems.py.merge-right.r5
 ?       lib/python/info/poems.py.working
-C       lib/python/info/poems.py
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<'__OUT__'
- M      .
+?       unversioned_file
 A  +    added_directory
 A  +    added_file
+A  +    module/tree_conflict_file
 C       lib/python/info/poems.py
-?       lib/python/info/poems.py.merge-left.r1
-?       lib/python/info/poems.py.merge-right.r5
-?       lib/python/info/poems.py.working
 M       module/hello_constants.f90
 M       module/hello_constants.inc
 M       module/hello_constants_dummy.inc
-A  +    module/tree_conflict_file
 M       subroutine/hello_sub_dummy.h
-?       unversioned_file
 Summary of conflicts:
   Text conflicts: 1
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 TEST_KEY=$TEST_KEY_BASE-merge-conflicts
@@ -147,34 +128,17 @@ file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 TEST_KEY=$TEST_KEY_BASE-merge-conflicts-status
 run_pass "$TEST_KEY" svn status --config-dir=$TEST_DIR/.subversion/
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<'__OUT__'
+status_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<'__OUT__'
  M      .
 ?       unversioned_file
-M       subroutine/hello_sub_dummy.h
-A  +    added_file
-A  +    module/tree_conflict_file
-M       module/hello_constants_dummy.inc
-M       module/hello_constants.inc
-M       module/hello_constants.f90
-A  +    added_directory
-A  +    added_directory/hello_constants_dummy.inc
-A  +    added_directory/hello_constants.inc
-A  +    added_directory/hello_constants.f90
-M       lib/python/info/poems.py
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<'__OUT__'
- M      .
 A  +    added_directory
 A  +    added_file
+A  +    module/tree_conflict_file
 M       lib/python/info/poems.py
 M       module/hello_constants.f90
 M       module/hello_constants.inc
 M       module/hello_constants_dummy.inc
-A  +    module/tree_conflict_file
 M       subroutine/hello_sub_dummy.h
-?       unversioned_file
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
diff --git a/t/fcm-conflicts/test_header b/t/fcm-conflicts/test_header
index 672ce12..6d52eac 100644
--- a/t/fcm-conflicts/test_header
+++ b/t/fcm-conflicts/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-diff/00-simple.t b/t/fcm-diff/00-simple.t
index b0cdf42..b59d899 100644
--- a/t/fcm-diff/00-simple.t
+++ b/t/fcm-diff/00-simple.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 3
 #-------------------------------------------------------------------------------
 setup
@@ -41,104 +42,9 @@ svn delete --force -q $FILE_DIR
 # Tests fcm branch-diff
 TEST_KEY=$TEST_KEY_BASE-fcm-diff
 run_pass "$TEST_KEY" fcm diff
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Index: added_file
-===================================================================
---- added_file	(revision 4)
-+++ added_file	(working copy)
-@@ -1 +1 @@
--INCLUDE 'hello_constants.inc'
-+INCLUDE 'hello_constants.INc'
-Index: module/hello_constants_dummy.inc
-===================================================================
---- module/hello_constants_dummy.inc	(revision 4)
-+++ module/hello_constants_dummy.inc	(working copy)
-@@ -1 +0,0 @@
--INCLUDE 'hello_constants.inc'
-Index: module/hello_constants.inc
-===================================================================
---- module/hello_constants.inc	(revision 4)
-+++ module/hello_constants.inc	(working copy)
-@@ -1 +0,0 @@
--CHARACTER (LEN=80), PARAMETER :: hello_string = 'Hello Earth!'
-Index: module/hello_constants.f90
-===================================================================
---- module/hello_constants.f90	(revision 4)
-+++ module/hello_constants.f90	(working copy)
-@@ -1,5 +0,0 @@
--MODULE Hello_Constants
--
--INCLUDE 'hello_constants_dummy.inc'
--
--END MODULE Hello_Constants
-Index: added_directory/hello_constants_dummy.inc
-===================================================================
---- added_directory/hello_constants_dummy.inc	(revision 4)
-+++ added_directory/hello_constants_dummy.inc	(working copy)
-@@ -1 +1 @@
--INCLUDE 'hello_constants.inc'
-+INCLUDE 'hello_constants.INc'
-Index: added_directory/hello_constants.inc
-===================================================================
---- added_directory/hello_constants.inc	(revision 4)
-+++ added_directory/hello_constants.inc	(working copy)
-@@ -1 +1,2 @@
--CHARACTER (LEN=80), PARAMETER :: hello_string = 'Hello Earth!'
-+CHARACTER (
-+LEN=80), PARAMETER :: hello_strINg = 'Hello Earth!!'
-Index: added_directory/hello_constants.f90
-===================================================================
---- added_directory/hello_constants.f90	(revision 4)
-+++ added_directory/hello_constants.f90	(working copy)
-@@ -1,5 +1,5 @@
- MODULE Hello_Constants
- 
--INCLUDE 'hello_constants_dummy.inc'
-+INCLUDE 'hello_constants_dummy.INc'
- 
- END MODULE Hello_Constants
-Index: lib/python/info/poems.py
-===================================================================
---- lib/python/info/poems.py	(revision 4)
-+++ lib/python/info/poems.py	(working copy)
-@@ -1,24 +1,23 @@
--#!/usr/bin/env python
--# -*- coding: utf-8 -*-
- """The Python, by Hilaire Belloc
- 
- A Python I should not advise,--
--It needs a doctor for its eyes,
-+It needs a doctor FOR its eyes,
- And has the measles yearly.
--However, if you feel inclined
--To get one (to improve your mind,
-+However, if you feel INclINed
-+To get one (
-+to improve your mINd,
- And not from fashion merely),
- Allow no music near its cage;
--And when it flies into a rage
-+And when it flies INto a rage
- Chastise it, most severely.
--I had an aunt in Yucatan
-+I had an aunt IN Yucatan
- Who bought a Python from a man
--And kept it for a pet.
-+And kept it FOR a pet.
- She died, because she never knew
- These simple little rules and few;--
--The Snake is living yet.
-+The Snake is livINg yet.
- """
- 
- import this
- 
--print "\n",  __doc__
-+prINt "\n",  __doc__
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+diff_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<'__OUT__'
+
 Index: added_directory/hello_constants.f90
 ===================================================================
 --- added_directory/hello_constants.f90	(revision 4)
@@ -233,7 +139,6 @@ Index: module/hello_constants_dummy.inc
 @@ -1 +0,0 @@
 -INCLUDE 'hello_constants.inc'
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 teardown
 #-------------------------------------------------------------------------------
diff --git a/t/fcm-diff/test_header b/t/fcm-diff/test_header
index 672ce12..6d52eac 100644
--- a/t/fcm-diff/test_header
+++ b/t/fcm-diff/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-install-svn-hook/00-basic.t b/t/fcm-install-svn-hook/00-basic.t
index d3947a2..0f61d0f 100755
--- a/t/fcm-install-svn-hook/00-basic.t
+++ b/t/fcm-install-svn-hook/00-basic.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -134,8 +134,8 @@ file_cmp "$TEST_KEY-ls-svnperms.conf" \
 # New install, single repository, with commit.conf
 TEST_KEY="$TEST_KEY_BASE-commit.conf"
 {
-    echo 'no-notify-branch-owner'
-    echo 'no-verify-branch-owner'
+    echo 'notify-branch-owner'
+    echo 'verify-branch-owner'
 } >'svn-import/commit.conf'
 NAME='commit-conf' run_tests
 file_cmp "$TEST_KEY-ls-svnperms.conf" \
diff --git a/t/fcm-install-svn-hook/01-housekeep-log.t b/t/fcm-install-svn-hook/01-housekeep-log.t
index f377876..e0734da 100755
--- a/t/fcm-install-svn-hook/01-housekeep-log.t
+++ b/t/fcm-install-svn-hook/01-housekeep-log.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-install-svn-hook/02-env.t b/t/fcm-install-svn-hook/02-env.t
index b3f26a4..33412c1 100644
--- a/t/fcm-install-svn-hook/02-env.t
+++ b/t/fcm-install-svn-hook/02-env.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-install-svn-hook/test_header_more b/t/fcm-install-svn-hook/test_header_more
index 2418b64..e059665 100644
--- a/t/fcm-install-svn-hook/test_header_more
+++ b/t/fcm-install-svn-hook/test_header_more
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-keyword-print/00-simple.t b/t/fcm-keyword-print/00-simple.t
index f22fd83..0b70a01 100755
--- a/t/fcm-keyword-print/00-simple.t
+++ b/t/fcm-keyword-print/00-simple.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-loc-layout/00-simple.t b/t/fcm-loc-layout/00-simple.t
index 55e902c..24a7e83 100644
--- a/t/fcm-loc-layout/00-simple.t
+++ b/t/fcm-loc-layout/00-simple.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-loc-layout/test_header b/t/fcm-loc-layout/test_header
index 6c38759..45ad994 100644
--- a/t/fcm-loc-layout/test_header
+++ b/t/fcm-loc-layout/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/00-build-basic.t b/t/fcm-make/00-build-basic.t
index 6b0c9ba..342d975 100755
--- a/t/fcm-make/00-build-basic.t
+++ b/t/fcm-make/00-build-basic.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/00-build-basic/bin/my-ld b/t/fcm-make/00-build-basic/bin/my-ld
index aff7d0e..5b69587 100755
--- a/t/fcm-make/00-build-basic/bin/my-ld
+++ b/t/fcm-make/00-build-basic/bin/my-ld
@@ -1,6 +1,6 @@
 #!/usr/bin/env bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/01-build-link-opts.t b/t/fcm-make/01-build-link-opts.t
index beb7396..e932248 100755
--- a/t/fcm-make/01-build-link-opts.t
+++ b/t/fcm-make/01-build-link-opts.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/02-build-ext-iface.t b/t/fcm-make/02-build-ext-iface.t
index 4c06975..843459e 100755
--- a/t/fcm-make/02-build-ext-iface.t
+++ b/t/fcm-make/02-build-ext-iface.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/02-build-ext-iface/expected/t1.interface b/t/fcm-make/02-build-ext-iface/expected/t1.interface
index 0ca0006..2c07df4 100644
--- a/t/fcm-make/02-build-ext-iface/expected/t1.interface
+++ b/t/fcm-make/02-build-ext-iface/expected/t1.interface
@@ -65,6 +65,12 @@ end subroutine sub_with_renamed_import
 subroutine sub_with_external(proc)
 external proc
 end subroutine sub_with_external
+subroutine sub_with_external2(PROC)
+external proc
+end subroutine sub_with_external2
+subroutine sub_with_external3(proc)
+external PROC
+end subroutine sub_with_external3
 subroutine sub_with_end()
 end subroutine sub_with_end
 end interface
diff --git a/t/fcm-make/02-build-ext-iface/src/t1.f90 b/t/fcm-make/02-build-ext-iface/src/t1.f90
index c7ce2f2..51a5bf7 100644
--- a/t/fcm-make/02-build-ext-iface/src/t1.f90
+++ b/t/fcm-make/02-build-ext-iface/src/t1.f90
@@ -147,6 +147,20 @@ external proc
 call proc()
 end subroutine sub_with_external
 
+! A subroutine with an external argument, 2
+! https://github.com/metomi/fcm/issues/175
+subroutine sub_with_external2(PROC)
+external proc
+call proc()
+end subroutine sub_with_external2
+
+! A subroutine with an external argument, 3
+! https://github.com/metomi/fcm/issues/175
+subroutine sub_with_external3(proc)
+external PROC
+call proc()
+end subroutine sub_with_external3
+
 ! A subroutine with a variable named "end"
 subroutine sub_with_end()
 integer :: end
diff --git a/t/fcm-make/03-build-include-paths.t b/t/fcm-make/03-build-include-paths.t
index 5d865f9..b483bb6 100755
--- a/t/fcm-make/03-build-include-paths.t
+++ b/t/fcm-make/03-build-include-paths.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/04-build-libs.t b/t/fcm-make/04-build-libs.t
index fce71cb..769779f 100755
--- a/t/fcm-make/04-build-libs.t
+++ b/t/fcm-make/04-build-libs.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/05-build-c-cxx-basic.t b/t/fcm-make/05-build-c-cxx-basic.t
index c3ec951..a46d185 100755
--- a/t/fcm-make/05-build-c-cxx-basic.t
+++ b/t/fcm-make/05-build-c-cxx-basic.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/06-extract-ssh.t b/t/fcm-make/06-extract-ssh.t
index 994aef1..56123f2 100755
--- a/t/fcm-make/06-extract-ssh.t
+++ b/t/fcm-make/06-extract-ssh.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/07-build-ns-dep.t b/t/fcm-make/07-build-ns-dep.t
index b938aa8..261cc87 100755
--- a/t/fcm-make/07-build-ns-dep.t
+++ b/t/fcm-make/07-build-ns-dep.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -60,9 +60,9 @@ file_cmp "$TEST_KEY.log" "$TEST_KEY.log" <<'__LOG__'
 [info] source->target main/hello.f90 -> (install) include/ hello.f90
 [info] source->target main/hello.f90 -> (compile) o/ hello.o
 [info] target hello.exe
+[info] target  - greet.o
 [info] target  - hello.o
 [info] target  - world.o
-[info] target  - greet.o
 __LOG__
 #-------------------------------------------------------------------------------
 exit 0
diff --git a/t/fcm-make/08-build-dup-dep.t b/t/fcm-make/08-build-dup-dep.t
index 8c51581..087f621 100755
--- a/t/fcm-make/08-build-dup-dep.t
+++ b/t/fcm-make/08-build-dup-dep.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -52,9 +52,9 @@ file_cmp "$TEST_KEY.log" "$TEST_KEY.log" <<'__LOG__'
 [info] source->target main/hello.f90 -> (install) include/ hello.f90
 [info] source->target main/hello.f90 -> (compile) o/ hello.o
 [info] target hello.exe
+[info] target  - greet.o
 [info] target  - hello.o
 [info] target  - world.o
-[info] target  - greet.o
 __LOG__
 #-------------------------------------------------------------------------------
 exit 0
diff --git a/t/fcm-make/09-build-dep-o.t b/t/fcm-make/09-build-dep-o.t
index 39b505d..64f4992 100755
--- a/t/fcm-make/09-build-dep-o.t
+++ b/t/fcm-make/09-build-dep-o.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -48,17 +48,17 @@ file_cmp "$TEST_KEY.log" "$TEST_KEY.log" <<'__LOG__'
 [info] source->target main/hi.f90 -> (install) include/ hi.f90
 [info] source->target main/hi.f90 -> (compile) o/ hi.o
 [info] target hi.exe
-[info] target  - hi.o
-[info] target  - world.o
 [info] target  - greet.o
 [info] target  -  - greet_fmt_mod.mod
 [info] target  -  -  - greet_fmt_mod.o
 [info] target  - greet_fmt_mod.o
-[info] target hello.exe
-[info] target  - hello.o
+[info] target  - hi.o
 [info] target  - world.o
+[info] target hello.exe
 [info] target  - greet.o (n-deps=1)
 [info] target  - greet_fmt_mod.o
+[info] target  - hello.o
+[info] target  - world.o
 __LOG__
 #-------------------------------------------------------------------------------
 exit 0
diff --git a/t/fcm-make/10-log.t b/t/fcm-make/10-log.t
index cc03bda..c59fc31 100755
--- a/t/fcm-make/10-log.t
+++ b/t/fcm-make/10-log.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -17,11 +17,11 @@
 # You should have received a copy of the GNU General Public License
 # along with FCM. If not, see <http://www.gnu.org/licenses/>.
 #-------------------------------------------------------------------------------
-# Basic tests for "fcm make".
+# Tests "fcm make", generation of log files.
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
-tests 7
+tests 11
 cp -r $TEST_SOURCE_DIR/$TEST_KEY_BASE/* .
 #-------------------------------------------------------------------------------
 TEST_KEY="$TEST_KEY_BASE"
@@ -40,6 +40,11 @@ if [[ $(ls .fcm-make/log-* | wc -l) == 1 ]]; then
 else
     fail "$TEST_KEY-n-logs"
 fi
+run_pass "$TEST_KEY-symlink-1" \
+    test "$(readlink 'fcm-make.log')" '=' '.fcm-make/log'
+run_pass "$TEST_KEY-symlink-2" \
+    test "$(readlink '.fcm-make/log')" \
+    '=' "$(cd '.fcm-make'; ls 'log-'* | sort | tail -1)"
 #-------------------------------------------------------------------------------
 TEST_KEY="$TEST_KEY_BASE-incr"
 sleep 1
@@ -50,5 +55,10 @@ if [[ $(ls .fcm-make/log-* | wc -l) == 2 ]]; then
 else
     fail "$TEST_KEY-n-logs"
 fi
+run_pass "$TEST_KEY-symlink-1" \
+    test "$(readlink 'fcm-make.log')" '=' '.fcm-make/log'
+run_pass "$TEST_KEY-symlink-2" \
+    test "$(readlink '.fcm-make/log')" \
+    '=' "$(cd '.fcm-make'; ls 'log-'* | sort | tail -1)"
 #-------------------------------------------------------------------------------
 exit 0
diff --git a/t/fcm-make/11-preprocess-include-path.t b/t/fcm-make/11-preprocess-include-path.t
index b3679f0..5448904 100755
--- a/t/fcm-make/11-preprocess-include-path.t
+++ b/t/fcm-make/11-preprocess-include-path.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/12-build-class-prop.t b/t/fcm-make/12-build-class-prop.t
index 0436c69..f55da45 100755
--- a/t/fcm-make/12-build-class-prop.t
+++ b/t/fcm-make/12-build-class-prop.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/13-build-target-prop.t b/t/fcm-make/13-build-target-prop.t
index 3af64be..6af8f14 100755
--- a/t/fcm-make/13-build-target-prop.t
+++ b/t/fcm-make/13-build-target-prop.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/13-build-target-prop/bin/my-fc b/t/fcm-make/13-build-target-prop/bin/my-fc
index a5afb0e..08b01ee 100755
--- a/t/fcm-make/13-build-target-prop/bin/my-fc
+++ b/t/fcm-make/13-build-target-prop/bin/my-fc
@@ -1,6 +1,6 @@
 #!/usr/bin/env bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/14-build-etc.t b/t/fcm-make/14-build-etc.t
index a1bfd07..8ff670e 100755
--- a/t/fcm-make/14-build-etc.t
+++ b/t/fcm-make/14-build-etc.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -47,8 +47,8 @@ foo                  <- foo
 hello.txt            <- hello.txt
 hi/hi-earth.txt      <- hi/hi-earth.txt
 hi/hi-mars.txt       <- hi/hi-mars.txt
-.etc                 <- 
 hi/.etc              <- hi
+.etc                 <- 
 __LOG__
 #-------------------------------------------------------------------------------
 TEST_KEY="$TEST_KEY_BASE-incr"
diff --git a/t/fcm-make/15-extract-loc-reset.t b/t/fcm-make/15-extract-loc-reset.t
index f124dc2..91ab664 100755
--- a/t/fcm-make/15-extract-loc-reset.t
+++ b/t/fcm-make/15-extract-loc-reset.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/16-build-dep-o-2.t b/t/fcm-make/16-build-dep-o-2.t
index 3622669..e8da6e0 100755
--- a/t/fcm-make/16-build-dep-o-2.t
+++ b/t/fcm-make/16-build-dep-o-2.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -41,10 +41,10 @@ file_cmp "$TEST_KEY.log" "$TEST_KEY.log" <<'__LOG__'
 [info] source->target hello_sub.f90 -> (compile) o/ hello_sub.o
 [info] target hello.exe
 [info] target  - hello.o
+[info] target  - hello_mod.o
 [info] target  - hello_sub.o
 [info] target  -  - hello_mod.mod
 [info] target  -  -  - hello_mod.o
-[info] target  - hello_mod.o
 __LOG__
 #-------------------------------------------------------------------------------
 exit 0
diff --git a/t/fcm-make/17-build-cyclic.t b/t/fcm-make/17-build-cyclic.t
index 713c14d..afda202 100755
--- a/t/fcm-make/17-build-cyclic.t
+++ b/t/fcm-make/17-build-cyclic.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -34,6 +34,8 @@ file_cmp "$TEST_KEY.err" "$TEST_KEY.err" <<'__ERR__'
 [FAIL]     required by: baz.mod
 [FAIL]     required by: foo.o
 [FAIL]     required by: foo.mod
+[FAIL]     required by: meow.o
+[FAIL]     required by: meow.mod
 [FAIL]     required by: hello.o
 [FAIL]     required by: hello.exe
 
diff --git a/t/fcm-make/18-build-use-intrinsic.t b/t/fcm-make/18-build-use-intrinsic.t
index ec6ceaa..54809a5 100755
--- a/t/fcm-make/18-build-use-intrinsic.t
+++ b/t/fcm-make/18-build-use-intrinsic.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -30,8 +30,8 @@ sed '/^\[info\] target /!d' .fcm-make/log >"$TEST_KEY.log"
 file_cmp "$TEST_KEY.log" "$TEST_KEY.log" <<'__LOG__'
 [info] target greet.exe
 [info] target  - greet.o
-[info] target  -  - hi.interface
 [info] target  -  - hello.interface
+[info] target  -  - hi.interface
 [info] target  - hello.o
 [info] target  - hi.o
 __LOG__
diff --git a/t/fcm-make/19-build-inherit-prop.t b/t/fcm-make/19-build-inherit-prop.t
index 6b1db5d..305a5d6 100755
--- a/t/fcm-make/19-build-inherit-prop.t
+++ b/t/fcm-make/19-build-inherit-prop.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/20-args.t b/t/fcm-make/20-args.t
index b60f227..3c02f92 100755
--- a/t/fcm-make/20-args.t
+++ b/t/fcm-make/20-args.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/21-inherit-steps.t b/t/fcm-make/21-inherit-steps.t
index 06607df..6111a60 100755
--- a/t/fcm-make/21-inherit-steps.t
+++ b/t/fcm-make/21-inherit-steps.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/22-build-2-bad-mod-over-inherit.t b/t/fcm-make/22-build-2-bad-mod-over-inherit.t
index 4cacfeb..48290e2 100755
--- a/t/fcm-make/22-build-2-bad-mod-over-inherit.t
+++ b/t/fcm-make/22-build-2-bad-mod-over-inherit.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/23-build-omp.t b/t/fcm-make/23-build-omp.t
index d370242..97124dd 100755
--- a/t/fcm-make/23-build-omp.t
+++ b/t/fcm-make/23-build-omp.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/24-build-c-main-camel.t b/t/fcm-make/24-build-c-main-camel.t
index 87604c5..dd0b48a 100755
--- a/t/fcm-make/24-build-c-main-camel.t
+++ b/t/fcm-make/24-build-c-main-camel.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/25-build-cyclic-2.t b/t/fcm-make/25-build-cyclic-2.t
index bfa79e5..baf837a 100755
--- a/t/fcm-make/25-build-cyclic-2.t
+++ b/t/fcm-make/25-build-cyclic-2.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/26-no-config.t b/t/fcm-make/26-no-config.t
index ce7ebe8..1fe5f8b 100755
--- a/t/fcm-make/26-no-config.t
+++ b/t/fcm-make/26-no-config.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/27-args-only.t b/t/fcm-make/27-args-only.t
index 59feaa4..e041046 100755
--- a/t/fcm-make/27-args-only.t
+++ b/t/fcm-make/27-args-only.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/28-bad-arg.t b/t/fcm-make/28-bad-arg.t
index fddb3db..725cde6 100755
--- a/t/fcm-make/28-bad-arg.t
+++ b/t/fcm-make/28-bad-arg.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/29-relative-cfg.t b/t/fcm-make/29-relative-cfg.t
index 3978621..12287b4 100755
--- a/t/fcm-make/29-relative-cfg.t
+++ b/t/fcm-make/29-relative-cfg.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/30-relative-cfg-in-svn.t b/t/fcm-make/30-relative-cfg-in-svn.t
index ca4fe2a..e9d9628 100755
--- a/t/fcm-make/30-relative-cfg-in-svn.t
+++ b/t/fcm-make/30-relative-cfg-in-svn.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/31-relative-cfg-in-ssh.t b/t/fcm-make/31-relative-cfg-in-ssh.t
index 21cd98d..f206455 100755
--- a/t/fcm-make/31-relative-cfg-in-ssh.t
+++ b/t/fcm-make/31-relative-cfg-in-ssh.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/32-include-relative-cfg.t b/t/fcm-make/32-include-relative-cfg.t
index 132def8..14514bf 100755
--- a/t/fcm-make/32-include-relative-cfg.t
+++ b/t/fcm-make/32-include-relative-cfg.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/33-include-relative-cfg-in-svn.t b/t/fcm-make/33-include-relative-cfg-in-svn.t
index 1eab85f..04e241e 100755
--- a/t/fcm-make/33-include-relative-cfg-in-svn.t
+++ b/t/fcm-make/33-include-relative-cfg-in-svn.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/34-include-relative-cfg-in-ssh.t b/t/fcm-make/34-include-relative-cfg-in-ssh.t
index 645e56d..6a24893 100755
--- a/t/fcm-make/34-include-relative-cfg-in-ssh.t
+++ b/t/fcm-make/34-include-relative-cfg-in-ssh.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/35-include-relative-cfg-in-2-dirs.t b/t/fcm-make/35-include-relative-cfg-in-2-dirs.t
index 1e0bb22..a89bec2 100755
--- a/t/fcm-make/35-include-relative-cfg-in-2-dirs.t
+++ b/t/fcm-make/35-include-relative-cfg-in-2-dirs.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-make/36-build-fail-cont-basic.t b/t/fcm-make/36-build-fail-cont-basic.t
old mode 100644
new mode 100755
index b62af82..d75f6b7
--- a/t/fcm-make/36-build-fail-cont-basic.t
+++ b/t/fcm-make/36-build-fail-cont-basic.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -43,9 +43,8 @@ sed -i 's/implicit none/implicit non/' src/greet_mod.f90  # introduce typo
 run_fail "$TEST_KEY" fcm make --new
 task_lines_from_log >"$TEST_KEY-log-tasks"
 file_cmp "$TEST_KEY-log-tasks" "$TEST_KEY-log-tasks" <<'__LOG__'
-[FAIL] compile   ???? ! greet_mod.o          <- greet_mod.f90
 [info] compile   ???? M world_mod.o          <- world_mod.f90
-[FAIL] compile   ---- ! hello.o              <- hello.f90
+[FAIL] compile   ???? ! greet_mod.o          <- greet_mod.f90
 [FAIL] compile   ---- ! hello2.o             <- hello2.f90
 [info] compile   ???? M hello_sub.o          <- hello_sub.f90
 [info] ext-iface ???? M hello_sub.interface  <- hello_sub.f90
@@ -58,8 +57,6 @@ fail_lines_from_log >"$TEST_KEY-log-fails"
 file_cmp "$TEST_KEY-log-fails" "$TEST_KEY-log-fails" <<'__LOG__'
 [FAIL] ! greet_mod.mod       : depends on failed target: greet_mod.o
 [FAIL] ! greet_mod.o         : update task failed
-[FAIL] ! hello               : depends on failed target: hello.o
-[FAIL] ! hello.o             : depends on failed target: greet_mod.mod
 [FAIL] ! hello2              : depends on failed target: hello2.o
 [FAIL] ! hello2.o            : depends on failed target: greet_mod.mod
 __LOG__
@@ -69,8 +66,8 @@ sed -i 's/implicit non/implicit none/' src/greet_mod.f90  # fix typo
 run_pass "$TEST_KEY" fcm make
 task_lines_from_log >"$TEST_KEY-log-tasks"
 file_cmp "$TEST_KEY-log-tasks" "$TEST_KEY-log-tasks" <<'__LOG__'
-[info] compile   ???? M greet_mod.o          <- greet_mod.f90
 [info] compile   ---- U world_mod.o          <- world_mod.f90
+[info] compile   ???? M greet_mod.o          <- greet_mod.f90
 [info] compile   ???? M hello.o              <- hello.f90
 [info] link      ???? M hello                <- hello.f90
 [info] compile   ???? M hello2.o             <- hello2.f90
@@ -91,8 +88,8 @@ sed -i 's/implicit none/implicit non/' src/hello_sub.f90  # introduce typo
 run_fail "$TEST_KEY" fcm make --new
 task_lines_from_log >"$TEST_KEY-log-tasks"
 file_cmp "$TEST_KEY-log-tasks" "$TEST_KEY-log-tasks" <<'__LOG__'
-[info] compile   ???? M greet_mod.o          <- greet_mod.f90
 [info] compile   ???? M world_mod.o          <- world_mod.f90
+[info] compile   ???? M greet_mod.o          <- greet_mod.f90
 [info] compile   ???? M hello.o              <- hello.f90
 [info] link      ???? M hello                <- hello.f90
 [info] compile   ???? M hello2.o             <- hello2.f90
@@ -116,8 +113,8 @@ sed -i 's/implicit non/implicit none/' src/hello_sub.f90  # fix typo
 run_pass "$TEST_KEY" fcm make
 task_lines_from_log >"$TEST_KEY-log-tasks"
 file_cmp "$TEST_KEY-log-tasks" "$TEST_KEY-log-tasks" <<'__LOG__'
-[info] compile   ---- U greet_mod.o          <- greet_mod.f90
 [info] compile   ---- U world_mod.o          <- world_mod.f90
+[info] compile   ---- U greet_mod.o          <- greet_mod.f90
 [info] compile   ---- U hello.o              <- hello.f90
 [info] link      ---- U hello                <- hello.f90
 [info] compile   ---- U hello2.o             <- hello2.f90
diff --git a/t/fcm-make/26-no-config.t b/t/fcm-make/37-no-such-config-file.t
similarity index 86%
copy from t/fcm-make/26-no-config.t
copy to t/fcm-make/37-no-such-config-file.t
index ce7ebe8..269fb52 100755
--- a/t/fcm-make/26-no-config.t
+++ b/t/fcm-make/37-no-such-config-file.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -17,16 +17,16 @@
 # You should have received a copy of the GNU General Public License
 # along with FCM. If not, see <http://www.gnu.org/licenses/>.
 #-------------------------------------------------------------------------------
-# Tests "fcm make", no configuration and no arguments.
+# Tests "fcm make", specified bad configuration file.
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
 tests 2
 #-------------------------------------------------------------------------------
 TEST_KEY="$TEST_KEY_BASE"
-run_fail "$TEST_KEY" fcm make
+run_fail "$TEST_KEY" fcm make -f bad-name.cfg
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" <<'__ERR__'
-[FAIL] no configuration specified or found
+[FAIL] bad-name.cfg: no such configuration file
 
 __ERR__
 #-------------------------------------------------------------------------------
diff --git a/t/fcm-make/38-extract-inherit-set-primary.t b/t/fcm-make/38-extract-inherit-set-primary.t
new file mode 100755
index 0000000..b8b86aa
--- /dev/null
+++ b/t/fcm-make/38-extract-inherit-set-primary.t
@@ -0,0 +1,79 @@
+#!/bin/bash
+#-------------------------------------------------------------------------------
+# (C) British Crown Copyright 2006-15 Met Office.
+#
+# This file is part of FCM, tools for managing and building source code.
+#
+# FCM is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# FCM is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with FCM. If not, see <http://www.gnu.org/licenses/>.
+#-------------------------------------------------------------------------------
+# Tests for "fcm make", "extract", location{primary} reset in inheritance.
+#-------------------------------------------------------------------------------
+. "$(dirname $0)/test_header"
+#-------------------------------------------------------------------------------
+tests 5
+#-------------------------------------------------------------------------------
+set -e
+svnadmin create 'repos'
+T_REPOS="file://${PWD}/repos"
+mkdir 't'
+echo "Hello World" >'t/hello.txt'
+echo "Hi World" >'t/hi.txt'
+svn import --no-auth-cache -q -m'Test' \
+    't/hello.txt' "${T_REPOS}/trunk/hello.txt"
+rm -fr 't'
+mkdir 'etc' 'i0' 'i1' 'junk'
+export FCM_CONF_PATH="${PWD}/etc"
+echo "location{primary}[t]=${T_REPOS}" >"${PWD}/etc/keyword.cfg"
+cat >'i0/fcm-make.cfg' <<__FCM_MAKE_CFG__
+steps=extract
+extract.ns=t
+extract.location{primary}[t]=${T_REPOS}
+__FCM_MAKE_CFG__
+fcm make -q -C 'i0'
+set +e
+#-------------------------------------------------------------------------------
+TEST_KEY="${TEST_KEY_BASE}-reset"
+cat >'i1/fcm-make.cfg' <<__FCM_MAKE_CFG__
+use=${PWD}/i0
+extract.location{primary}[t]=${PWD}/junk
+__FCM_MAKE_CFG__
+run_fail "${TEST_KEY}" fcm make --new -C 'i1'
+file_cmp "${TEST_KEY}.err" "${TEST_KEY}.err" <<__ERR__
+[FAIL] extract.location{primary}[t] = ${PWD}/junk: cannot modify, value is inherited
+[FAIL] config-file=${PWD}/i1/fcm-make.cfg:1
+
+__ERR__
+#-------------------------------------------------------------------------------
+TEST_KEY="${TEST_KEY_BASE}-set-identical"
+cat >'i1/fcm-make.cfg' <<__FCM_MAKE_CFG__
+use=${PWD}/i0
+extract.location{primary}[t]=${T_REPOS}
+__FCM_MAKE_CFG__
+run_pass "${TEST_KEY}" fcm make --new -C 'i1'
+#-------------------------------------------------------------------------------
+TEST_KEY="${TEST_KEY_BASE}-set-same-1"
+cat >'i1/fcm-make.cfg' <<__FCM_MAKE_CFG__
+use=${PWD}/i0
+extract.location{primary}[t]=${T_REPOS}/
+__FCM_MAKE_CFG__
+run_pass "${TEST_KEY}" fcm make --new -C 'i1'
+#-------------------------------------------------------------------------------
+TEST_KEY="${TEST_KEY_BASE}-set-same-2"
+cat >'i1/fcm-make.cfg' <<__FCM_MAKE_CFG__
+use=${PWD}/i0
+extract.location{primary}[t]=fcm:t
+__FCM_MAKE_CFG__
+run_pass "${TEST_KEY}" fcm make --new -C 'i1'
+#-------------------------------------------------------------------------------
+exit 0
diff --git a/t/fcm-make/32-include-relative-cfg.t b/t/fcm-make/39-build-source-with-dot.t
similarity index 59%
copy from t/fcm-make/32-include-relative-cfg.t
copy to t/fcm-make/39-build-source-with-dot.t
index 132def8..8fa0dcb 100755
--- a/t/fcm-make/32-include-relative-cfg.t
+++ b/t/fcm-make/39-build-source-with-dot.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -17,38 +17,38 @@
 # You should have received a copy of the GNU General Public License
 # along with FCM. If not, see <http://www.gnu.org/licenses/>.
 #-------------------------------------------------------------------------------
-# Tests "fcm make", include relative config
+# Tests "fcm make", build, source path is under a hidden directory.
 #-------------------------------------------------------------------------------
-. $(dirname $0)/test_header
+. "$(dirname "$0")/test_header"
+tests 5
 #-------------------------------------------------------------------------------
-tests 6
-#-------------------------------------------------------------------------------
-mkdir etc
-cat >etc/fcm-make-build.cfg <<'__CFG__'
-steps=build
-build.source=src
-build.target=hello.exe
-__CFG__
-
-mkdir src
-cat >src/hello.f90 <<'__FORTRAN__'
+mkdir -p 'src/.singularity'
+cat >'src/.singularity/hello.f90' <<'__FORTRAN__'
 program hello
-write(*, '(a)') 'Hello World!'
+write(*, '(a)') 'No information!'
 end program hello
 __FORTRAN__
-
 #-------------------------------------------------------------------------------
-cat >fcm-make.cfg <<'__CFG__'
-include = fcm-make-build.cfg
+cat >'fcm-make.cfg' <<'__CFG__'
+steps=build
+build.source=$HERE/src
+build.prop{file-ext.bin}=.bin
+build.target=hello.bin
 __CFG__
+run_fail "${TEST_KEY_BASE}-tail" fcm make --new
+run_fail "${TEST_KEY_BASE}-tail.bin" './build/bin/hello.bin'
 
-fcm_make_build_hello_tests "$TEST_KEY_BASE-config-file-path" '.exe' -F $PWD/etc
-#-------------------------------------------------------------------------------
-cat >fcm-make.cfg <<'__CFG__'
-include-path=$HERE/etc
-include=fcm-make-build.cfg
+cat >'fcm-make.cfg' <<'__CFG__'
+steps=build
+build.source=$HERE/src/.singularity
+build.prop{file-ext.bin}=.bin
+build.target=hello.bin
 __CFG__
-
-fcm_make_build_hello_tests "$TEST_KEY_BASE-include-path" '.exe'
-#-------------------------------------------------------------------------------
-exit 0
+run_pass "${TEST_KEY_BASE}-head" fcm make --new
+run_pass "${TEST_KEY_BASE}-head.bin" './build/bin/hello.bin'
+file_cmp "${TEST_KEY_BASE}-head.bin.out" \
+    "${TEST_KEY_BASE}-head.bin.out" <<'__OUT__'
+No information!
+__OUT__
+#-------------------------------------------------------------------------------
+exit
diff --git a/t/fcm-make/35-include-relative-cfg-in-2-dirs.t b/t/fcm-make/40-extract-fs-source-with-dot.t
similarity index 53%
copy from t/fcm-make/35-include-relative-cfg-in-2-dirs.t
copy to t/fcm-make/40-extract-fs-source-with-dot.t
index 1e0bb22..78cb2cc 100755
--- a/t/fcm-make/35-include-relative-cfg-in-2-dirs.t
+++ b/t/fcm-make/40-extract-fs-source-with-dot.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -17,46 +17,43 @@
 # You should have received a copy of the GNU General Public License
 # along with FCM. If not, see <http://www.gnu.org/licenses/>.
 #-------------------------------------------------------------------------------
-# Tests "fcm make", include relative config
+# Tests "fcm make", extract, FS source path is under a hidden directory.
 #-------------------------------------------------------------------------------
-. $(dirname $0)/test_header
+. "$(dirname "$0")/test_header"
+tests 5
 #-------------------------------------------------------------------------------
-tests 6
-#-------------------------------------------------------------------------------
-mkdir cfg1 cfg2
-cat >cfg1/fcm-make-head.cfg <<'__CFG__'
-steps=build
-build.source=src
-__CFG__
-cat >cfg1/fcm-make-tail.cfg <<'__CFG__'
-build.target=hello.exe
-__CFG__
-cat >cfg2/fcm-make-tail.cfg <<'__CFG__'
-build.target=hello
-build.prop{file-ext.bin}=
-__CFG__
-
-mkdir src
-cat >src/hello.f90 <<'__FORTRAN__'
-program hello
-write(*, '(a)') 'Hello World!'
-end program hello
+# dot path name under source tree
+mkdir -p 'bubble/.com'
+cat >'bubble/.com/burst.f90' <<'__FORTRAN__'
+program burst
+write(*, '(a)') 'Burst!'
+end program burst
 __FORTRAN__
-
-#-------------------------------------------------------------------------------
-cat >fcm-make.cfg <<'__CFG__'
-include-path = $HERE/cfg1 $HERE/cfg2
-include = fcm-make-head.cfg fcm-make-tail.cfg
+cat >'fcm-make.cfg' <<'__CFG__'
+steps=extract
+extract.ns = bubble
+extract.location[bubble]=$HERE/bubble
 __CFG__
-
-fcm_make_build_hello_tests "$TEST_KEY_BASE-1" '.exe'
-#-------------------------------------------------------------------------------
-cat >fcm-make.cfg <<'__CFG__'
-include-path = $HERE/cfg2
-include-path{+} = $HERE/cfg1
-include = fcm-make-head.cfg fcm-make-tail.cfg
+run_pass "${TEST_KEY_BASE}-tail" fcm make --new
+run_fail "${TEST_KEY_BASE}-tail-find" find 'extract' -type f
+#-------------------------------------------------------------------------------
+# dot path name above source tree
+mkdir -p '.com/bubble'
+cat >'.com/bubble/burst.f90' <<'__FORTRAN__'
+program burst
+write(*, '(a)') 'Burst!'
+end program burst
+__FORTRAN__
+cat >'fcm-make.cfg' <<'__CFG__'
+steps=extract
+extract.ns = bubble
+extract.location[bubble]=$HERE/.com/bubble
 __CFG__
-
-fcm_make_build_hello_tests "$TEST_KEY_BASE-2" ''
-#-------------------------------------------------------------------------------
-exit 0
+run_pass "${TEST_KEY_BASE}-head" fcm make --new
+run_pass "${TEST_KEY_BASE}-head-find" find 'extract' -type f
+file_cmp "${TEST_KEY_BASE}-head-find.out" \
+    "${TEST_KEY_BASE}-head-find.out" <<'__OUT__'
+extract/bubble/burst.f90
+__OUT__
+#-------------------------------------------------------------------------------
+exit
diff --git a/t/fcm-make/41-ctx-name.t b/t/fcm-make/41-ctx-name.t
new file mode 100755
index 0000000..f57a6d2
--- /dev/null
+++ b/t/fcm-make/41-ctx-name.t
@@ -0,0 +1,177 @@
+#!/bin/bash
+#-------------------------------------------------------------------------------
+# (C) British Crown Copyright 2006-15 Met Office.
+#
+# This file is part of FCM, tools for managing and building source code.
+#
+# FCM is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# FCM is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with FCM. If not, see <http://www.gnu.org/licenses/>.
+#-------------------------------------------------------------------------------
+# Tests "fcm make", context name.
+#-------------------------------------------------------------------------------
+. "$(dirname "$0")/test_header"
+
+find_fcm_make_files() {
+    find . "$@" -type f \
+        '(' -path '*/build/*' -o \
+            -path '*/extract/*' -o \
+            -path '*/.fcm-make*/c*' ')' \
+        | sort
+}
+
+tests 17
+
+mkdir -p 'src/a' 'src/b'
+cat >'src/a/a.f90' <<'__FORTRAN__'
+program a
+write(*, '(a)') 'I am program A.'
+end program a
+__FORTRAN__
+cat >'src/b/b.f90' <<'__FORTRAN__'
+program b
+write(*, '(a)') 'I am program B.'
+end program b
+__FORTRAN__
+
+cat >'fcm-make.cfg' <<'__CFG__'
+steps=extract
+extract.ns = a
+extract.location[a]=$HERE/src/a
+__CFG__
+
+cat >'fcm-make2.cfg' <<'__CFG__'
+name=2
+steps=build
+build.source=extract src/b
+build.target{task}=link
+__CFG__
+#-------------------------------------------------------------------------------
+run_pass "${TEST_KEY_BASE}-1" fcm make
+find_fcm_make_files >"${TEST_KEY_BASE}-1.find.new"
+file_cmp "${TEST_KEY_BASE}-1.find.new" "${TEST_KEY_BASE}-1.find.new" <<'__FIND__'
+./.fcm-make/config-as-parsed.cfg
+./.fcm-make/config-on-success.cfg
+./.fcm-make/ctx.gz
+./extract/a/a.f90
+__FIND__
+
+touch 'marker'
+sleep 1
+run_pass "${TEST_KEY_BASE}-2" fcm make --name=2
+find_fcm_make_files '!' -newer 'marker' >"${TEST_KEY_BASE}-2.find.old"
+file_cmp "${TEST_KEY_BASE}-2.find.old" \
+    "${TEST_KEY_BASE}-2.find.old" "${TEST_KEY_BASE}-1.find.new"
+find_fcm_make_files -newer 'marker' >"${TEST_KEY_BASE}-2.find.new"
+file_cmp "${TEST_KEY_BASE}-2.find.new" "${TEST_KEY_BASE}-2.find.new" <<'__FIND__'
+./.fcm-make2/config-as-parsed.cfg
+./.fcm-make2/config-on-success.cfg
+./.fcm-make2/ctx.gz
+./build/bin/a.exe
+./build/bin/b.exe
+./build/o/a.o
+./build/o/b.o
+__FIND__
+
+touch 'marker'
+sleep 1
+run_pass "${TEST_KEY_BASE}-1-incr" fcm make
+find_fcm_make_files '!' -newer 'marker' >"${TEST_KEY_BASE}-1-incr.find.old"
+file_cmp "${TEST_KEY_BASE}-1-incr.find.old" \
+    "${TEST_KEY_BASE}-1-incr.find.old" <<'__FIND__'
+./.fcm-make2/config-as-parsed.cfg
+./.fcm-make2/config-on-success.cfg
+./.fcm-make2/ctx.gz
+./build/bin/a.exe
+./build/bin/b.exe
+./build/o/a.o
+./build/o/b.o
+./extract/a/a.f90
+__FIND__
+find_fcm_make_files -newer 'marker' >"${TEST_KEY_BASE}-1-incr.find.new"
+file_cmp "${TEST_KEY_BASE}-1-incr.find.new" \
+    "${TEST_KEY_BASE}-1-incr.find.new" <<'__FIND__'
+./.fcm-make/config-as-parsed.cfg
+./.fcm-make/config-on-success.cfg
+./.fcm-make/ctx.gz
+__FIND__
+
+touch 'marker'
+sleep 1
+run_pass "${TEST_KEY_BASE}-2-incr" fcm make --name=2
+find_fcm_make_files '!' -newer 'marker' >"${TEST_KEY_BASE}-2-incr.find.old"
+file_cmp "${TEST_KEY_BASE}-2-incr.find.old" \
+    "${TEST_KEY_BASE}-2-incr.find.old" <<'__FIND__'
+./.fcm-make/config-as-parsed.cfg
+./.fcm-make/config-on-success.cfg
+./.fcm-make/ctx.gz
+./build/bin/a.exe
+./build/bin/b.exe
+./build/o/a.o
+./build/o/b.o
+./extract/a/a.f90
+__FIND__
+find_fcm_make_files -newer 'marker' >"${TEST_KEY_BASE}-2-incr.find.new"
+file_cmp "${TEST_KEY_BASE}-2-incr.find.new" \
+    "${TEST_KEY_BASE}-2-incr.find.new" <<'__FIND__'
+./.fcm-make2/config-as-parsed.cfg
+./.fcm-make2/config-on-success.cfg
+./.fcm-make2/ctx.gz
+__FIND__
+
+touch 'marker'
+sleep 1
+run_pass "${TEST_KEY_BASE}-1-new" fcm make --new
+find_fcm_make_files '!' -newer 'marker' >"${TEST_KEY_BASE}-1-new.find.old"
+file_cmp "${TEST_KEY_BASE}-1-new.find.old" \
+    "${TEST_KEY_BASE}-1-new.find.old" <<'__FIND__'
+./.fcm-make2/config-as-parsed.cfg
+./.fcm-make2/config-on-success.cfg
+./.fcm-make2/ctx.gz
+./build/bin/a.exe
+./build/bin/b.exe
+./build/o/a.o
+./build/o/b.o
+__FIND__
+find_fcm_make_files -newer 'marker' >"${TEST_KEY_BASE}-1-new.find.new"
+file_cmp "${TEST_KEY_BASE}-1-new.find.new" \
+    "${TEST_KEY_BASE}-1-new.find.new" <<'__FIND__'
+./.fcm-make/config-as-parsed.cfg
+./.fcm-make/config-on-success.cfg
+./.fcm-make/ctx.gz
+./extract/a/a.f90
+__FIND__
+
+touch 'marker'
+sleep 1
+run_pass "${TEST_KEY_BASE}-2-new" fcm make --name=2 --new
+find_fcm_make_files '!' -newer 'marker' >"${TEST_KEY_BASE}-2-new.find.old"
+file_cmp "${TEST_KEY_BASE}-2-new.find.old" \
+    "${TEST_KEY_BASE}-2-new.find.old" <<'__FIND__'
+./.fcm-make/config-as-parsed.cfg
+./.fcm-make/config-on-success.cfg
+./.fcm-make/ctx.gz
+./extract/a/a.f90
+__FIND__
+find_fcm_make_files -newer 'marker' >"${TEST_KEY_BASE}-2-new.find.new"
+file_cmp "${TEST_KEY_BASE}-2-new.find.new" \
+    "${TEST_KEY_BASE}-2-new.find.new" <<'__FIND__'
+./.fcm-make2/config-as-parsed.cfg
+./.fcm-make2/config-on-success.cfg
+./.fcm-make2/ctx.gz
+./build/bin/a.exe
+./build/bin/b.exe
+./build/o/a.o
+./build/o/b.o
+__FIND__
+#-------------------------------------------------------------------------------
+exit
diff --git a/t/fcm-make/42-make-mirror-make2.t b/t/fcm-make/42-make-mirror-make2.t
new file mode 100755
index 0000000..9f0dc55
--- /dev/null
+++ b/t/fcm-make/42-make-mirror-make2.t
@@ -0,0 +1,125 @@
+#!/bin/bash
+#-------------------------------------------------------------------------------
+# (C) British Crown Copyright 2006-15 Met Office.
+#
+# This file is part of FCM, tools for managing and building source code.
+#
+# FCM is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# FCM is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with FCM. If not, see <http://www.gnu.org/licenses/>.
+#-------------------------------------------------------------------------------
+# Tests "fcm make" with mirror to same location, then "fcm make --name=2".
+#-------------------------------------------------------------------------------
+. "$(dirname "$0")/test_header"
+
+find_fcm_make_files() {
+    find . "$@" -type f \
+        '(' -path '*/build/*' -o \
+            -path '*/extract/*' -o \
+            -path '*/mirror/*' -o \
+            -path '*/.fcm-make*/c*' ')' \
+        | sort
+}
+
+tests 11
+
+mkdir -p 'src/hello'
+cat >'src/hello/hello.f90' <<'__FORTRAN__'
+program hello
+write(*, '(a)') 'Hello!'
+end program hello
+__FORTRAN__
+
+cat >'fcm-make.cfg' <<'__CFG__'
+steps=extract mirror
+extract.ns = hello
+extract.location[hello]=$HERE/src/hello
+mirror.target=$HERE
+mirror.prop{config-file.name}=2
+mirror.prop{config-file.steps}=build
+build.target{task}=link
+__CFG__
+
+#-------------------------------------------------------------------------------
+run_pass "${TEST_KEY_BASE}-1" fcm make
+find_fcm_make_files >"${TEST_KEY_BASE}-1.find.new"
+file_cmp "${TEST_KEY_BASE}-1.find.new" "${TEST_KEY_BASE}-1.find.new" <<'__FIND__'
+./.fcm-make/config-as-parsed.cfg
+./.fcm-make/config-on-success.cfg
+./.fcm-make/ctx.gz
+./extract/hello/hello.f90
+./mirror/fcm-make2.cfg
+./mirror/fcm-make2.cfg.orig
+__FIND__
+
+touch 'marker'
+sleep 1
+run_pass "${TEST_KEY_BASE}-2" fcm make -f fcm-make2.cfg
+find_fcm_make_files '!' -newer 'marker' >"${TEST_KEY_BASE}-2.find.old"
+file_cmp "${TEST_KEY_BASE}-2.find.old" \
+    "${TEST_KEY_BASE}-2.find.old" "${TEST_KEY_BASE}-1.find.new"
+find_fcm_make_files -newer 'marker' >"${TEST_KEY_BASE}-2.find.new"
+file_cmp "${TEST_KEY_BASE}-2.find.new" "${TEST_KEY_BASE}-2.find.new" <<'__FIND__'
+./.fcm-make2/config-as-parsed.cfg
+./.fcm-make2/config-on-success.cfg
+./.fcm-make2/ctx.gz
+./build/bin/hello.exe
+./build/o/hello.o
+__FIND__
+
+touch 'marker'
+sleep 1
+run_pass "${TEST_KEY_BASE}-1-incr" fcm make
+find_fcm_make_files '!' -newer 'marker' >"${TEST_KEY_BASE}-1-incr.find.old"
+file_cmp "${TEST_KEY_BASE}-1-incr.find.old" \
+    "${TEST_KEY_BASE}-1-incr.find.old" <<'__FIND__'
+./.fcm-make2/config-as-parsed.cfg
+./.fcm-make2/config-on-success.cfg
+./.fcm-make2/ctx.gz
+./build/bin/hello.exe
+./build/o/hello.o
+./extract/hello/hello.f90
+__FIND__
+find_fcm_make_files -newer 'marker' >"${TEST_KEY_BASE}-1-incr.find.new"
+file_cmp "${TEST_KEY_BASE}-1-incr.find.new" \
+    "${TEST_KEY_BASE}-1-incr.find.new" <<'__FIND__'
+./.fcm-make/config-as-parsed.cfg
+./.fcm-make/config-on-success.cfg
+./.fcm-make/ctx.gz
+./mirror/fcm-make2.cfg
+./mirror/fcm-make2.cfg.orig
+__FIND__
+
+touch 'marker'
+sleep 1
+run_pass "${TEST_KEY_BASE}-2-incr" fcm make -f fcm-make2.cfg
+find_fcm_make_files '!' -newer 'marker' >"${TEST_KEY_BASE}-2-incr.find.old"
+file_cmp "${TEST_KEY_BASE}-2-incr.find.old" \
+    "${TEST_KEY_BASE}-2-incr.find.old" <<'__FIND__'
+./.fcm-make/config-as-parsed.cfg
+./.fcm-make/config-on-success.cfg
+./.fcm-make/ctx.gz
+./build/bin/hello.exe
+./build/o/hello.o
+./extract/hello/hello.f90
+./mirror/fcm-make2.cfg
+./mirror/fcm-make2.cfg.orig
+__FIND__
+find_fcm_make_files -newer 'marker' >"${TEST_KEY_BASE}-2-incr.find.new"
+file_cmp "${TEST_KEY_BASE}-2-incr.find.new" \
+    "${TEST_KEY_BASE}-2-incr.find.new" <<'__FIND__'
+./.fcm-make2/config-as-parsed.cfg
+./.fcm-make2/config-on-success.cfg
+./.fcm-make2/ctx.gz
+__FIND__
+#-------------------------------------------------------------------------------
+exit
diff --git a/t/fcm-make/43-ctx-name-inherit.t b/t/fcm-make/43-ctx-name-inherit.t
new file mode 100755
index 0000000..cca4557
--- /dev/null
+++ b/t/fcm-make/43-ctx-name-inherit.t
@@ -0,0 +1,98 @@
+#!/bin/bash
+#-------------------------------------------------------------------------------
+# (C) British Crown Copyright 2006-15 Met Office.
+#
+# This file is part of FCM, tools for managing and building source code.
+#
+# FCM is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# FCM is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with FCM. If not, see <http://www.gnu.org/licenses/>.
+#-------------------------------------------------------------------------------
+# Tests "fcm make", inherit, with context name.
+#-------------------------------------------------------------------------------
+. "$(dirname "$0")/test_header"
+
+find_fcm_make_files() {
+    find . "$@" -type f \
+        '(' -path '*/build/*' -o \
+            -path '*/extract/*' -o \
+            -path '*/.fcm-make*/c*' ')' \
+        | sort
+}
+
+tests 5
+
+#-------------------------------------------------------------------------------
+mkdir -p 'hello/src'
+cat >'hello/fcm-make-friend.cfg' <<'__CFG__'
+name=-friend
+steps=build
+build.source=$HERE/src
+build.target{task}=link
+__CFG__
+cat >'hello/src/friend.f90' <<'__FORTRAN__'
+module friend
+character(*), parameter :: name = 'friend'
+end module friend
+__FORTRAN__
+cat >'hello/src/hello.f90' <<'__FORTRAN__'
+program hello
+use friend, only: name
+write(*, '(a,1x,a)') 'Hello', name
+end program hello
+__FORTRAN__
+
+run_pass "${TEST_KEY_BASE}-hello" fcm make -C "${PWD}/hello" -n '-friend'
+#-------------------------------------------------------------------------------
+mkdir -p 'greet/src'
+cat >'greet/fcm-make-friend.cfg' <<'__CFG__'
+use=$HERE/../hello
+name=-friend
+steps=build
+build.source=$HERE/src
+build.target{task}=link
+__CFG__
+cat >'greet/src/greet.f90' <<'__FORTRAN__'
+program greet
+use friend, only: name
+write(*, '(a,1x,a)') 'Greet', name
+end program greet
+__FORTRAN__
+
+run_pass "${TEST_KEY_BASE}-greet" fcm make -C "${PWD}/greet" -n '-friend'
+(cd 'greet' && find_fcm_make_files) >"${TEST_KEY_BASE}-greet.find"
+file_cmp "${TEST_KEY_BASE}-greet.find" "${TEST_KEY_BASE}-greet.find" <<'__FIND__'
+./.fcm-make-friend/config-as-parsed.cfg
+./.fcm-make-friend/config-on-success.cfg
+./.fcm-make-friend/ctx.gz
+./build/bin/greet.exe
+./build/bin/hello.exe
+./build/o/greet.o
+__FIND__
+#-------------------------------------------------------------------------------
+mkdir -p 'snub/src'
+cat >'snub/fcm-make-no-friend.cfg' <<'__CFG__'
+use=$HERE/../hello
+name=-no-friend
+steps=build
+build.source=$HERE/src
+build.target{task}=link
+__CFG__
+run_fail "${TEST_KEY_BASE}-snub" fcm make -C "${PWD}/snub" -n '-no-friend'
+sed -i '3q' "${TEST_KEY_BASE}-snub.err"  # 3 lines only
+file_cmp "${TEST_KEY_BASE}-snub.err" "${TEST_KEY_BASE}-snub.err" <<__ERR__
+[FAIL] use = ${PWD}/hello: incorrect value in declaration
+[FAIL] config-file=${PWD}/snub/fcm-make-no-friend.cfg:1
+[FAIL] ${PWD}/hello/.fcm-make/ctx.gz: cannot retrieve cache
+__ERR__
+#-------------------------------------------------------------------------------
+exit
diff --git a/t/fcm-make/44-ctx-name-inherit-compat.t b/t/fcm-make/44-ctx-name-inherit-compat.t
new file mode 100755
index 0000000..350f1fc
--- /dev/null
+++ b/t/fcm-make/44-ctx-name-inherit-compat.t
@@ -0,0 +1,92 @@
+#!/bin/bash
+#-------------------------------------------------------------------------------
+# (C) British Crown Copyright 2006-15 Met Office.
+#
+# This file is part of FCM, tools for managing and building source code.
+#
+# FCM is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# FCM is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with FCM. If not, see <http://www.gnu.org/licenses/>.
+#-------------------------------------------------------------------------------
+# Tests "fcm make", inherit, with context name, back compat.
+#-------------------------------------------------------------------------------
+. "$(dirname "$0")/test_header"
+
+find_fcm_make_files() {
+    find . "$@" -type f \
+        '(' -path '*/build/*' -o \
+            -path '*/extract/*' -o \
+            -path '*/.fcm-make*/c*' ')' \
+        | sort
+}
+
+tests 2
+
+#-------------------------------------------------------------------------------
+mkdir -p 'hello/src'
+cat >'hello/fcm-make.cfg' <<'__CFG__'
+steps=build
+build.source=$HERE/src
+build.target{task}=link
+__CFG__
+cat >'hello/src/friend.f90' <<'__FORTRAN__'
+module friend
+character(*), parameter :: name = 'friend'
+end module friend
+__FORTRAN__
+cat >'hello/src/hello.f90' <<'__FORTRAN__'
+program hello
+use friend, only: name
+write(*, '(a,1x,a)') 'Hello', name
+end program hello
+__FORTRAN__
+
+fcm make -q -C "${PWD}/hello"
+
+# Remove "name" from make ctx to make it look like a make ctx generated from an
+# old version of "fcm make".
+gunzip "${PWD}/hello/.fcm-make/ctx.gz"
+perl - "${PWD}/hello/.fcm-make/ctx" <<'__PERL__'
+use Storable qw{nstore retrieve};
+my $m_ctx = retrieve($ARGV[0]);
+delete $m_ctx->{'name'};
+nstore($m_ctx, $ARGV[0]);
+__PERL__
+gzip "${PWD}/hello/.fcm-make/ctx"
+#-------------------------------------------------------------------------------
+mkdir -p 'greet/src'
+cat >'greet/fcm-make-friend.cfg' <<'__CFG__'
+use=$HERE/../hello
+name=-friend
+steps=build
+build.source=$HERE/src
+build.target{task}=link
+__CFG__
+cat >'greet/src/greet.f90' <<'__FORTRAN__'
+program greet
+use friend, only: name
+write(*, '(a,1x,a)') 'Greet', name
+end program greet
+__FORTRAN__
+
+run_pass "${TEST_KEY_BASE}" fcm make -C "${PWD}/greet" -n '-friend'
+(cd 'greet' && find_fcm_make_files) >"${TEST_KEY_BASE}.find"
+file_cmp "${TEST_KEY_BASE}.find" "${TEST_KEY_BASE}.find" <<'__FIND__'
+./.fcm-make-friend/config-as-parsed.cfg
+./.fcm-make-friend/config-on-success.cfg
+./.fcm-make-friend/ctx.gz
+./build/bin/greet.exe
+./build/bin/hello.exe
+./build/o/greet.o
+__FIND__
+#-------------------------------------------------------------------------------
+exit
diff --git a/t/fcm-make/45-dest-mv.t b/t/fcm-make/45-dest-mv.t
new file mode 100755
index 0000000..0443c2e
--- /dev/null
+++ b/t/fcm-make/45-dest-mv.t
@@ -0,0 +1,85 @@
+#!/bin/bash
+#-------------------------------------------------------------------------------
+# (C) British Crown Copyright 2006-15 Met Office.
+#
+# This file is part of FCM, tools for managing and building source code.
+#
+# FCM is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# FCM is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with FCM. If not, see <http://www.gnu.org/licenses/>.
+#-------------------------------------------------------------------------------
+# Tests "fcm make", destination moved.
+#-------------------------------------------------------------------------------
+. "$(dirname "$0")/test_header"
+
+tests 9
+
+mkdir -p 'src/hello'
+cat >'src/hello/hello.f90' <<'__FORTRAN__'
+program hello
+use greet_mod, only: greet
+use world_mod, only: world
+write(*, '(a,1x,a)') greet, world
+end program hello
+__FORTRAN__
+cat >'src/hello/world_mod.f90' <<'__FORTRAN__'
+module world_mod
+character(*), parameter :: world = 'Earth'
+end module world_mod
+__FORTRAN__
+cat >'src/hello/greet_mod.f90' <<'__FORTRAN__'
+module greet_mod
+character(*), parameter :: greet = 'Hello'
+end module greet_mod
+__FORTRAN__
+
+svnadmin create 'hello.svn'
+URL="file://${PWD}/hello.svn/hello"
+svn import --no-auth-cache -m'initial import' 'src' "${URL}/trunk/src"
+
+mkdir -p 'loc1'
+cat >'loc1/fcm-make.cfg' <<__CFG__
+steps=extract build
+extract.ns=hello
+extract.location{primary}[hello]=${URL}
+build.target{task}=link
+build.prop{file-ext.bin}=
+__CFG__
+#-------------------------------------------------------------------------------
+run_pass "${TEST_KEY_BASE}-1" fcm make -C "${PWD}/loc1"
+mv "${PWD}/loc1" "${PWD}/loc2"
+#-------------------------------------------------------------------------------
+# Inherit
+mkdir -p 'loc3'
+cat >'loc3/fcm-make.cfg' <<__CFG__
+use=${PWD}/loc2
+__CFG__
+run_pass "${TEST_KEY_BASE}-3" fcm make -C "${PWD}/loc3"
+LOG="${PWD}/loc3/fcm-make.log"
+file_grep "${TEST_KEY_BASE}-3-log-1" \
+    '\[info\]   dest:    3 \[U unchanged\]' "${LOG}"
+file_grep "${TEST_KEY_BASE}-3-log-2" \
+    '\[info\] sources: total=3, analysed=0' "${LOG}"
+file_grep "${TEST_KEY_BASE}-3-log-3" \
+    '\[info\] TOTAL     targets: modified=0, unchanged=6, failed=0' "${LOG}"
+#-------------------------------------------------------------------------------
+# Incremental
+run_pass "${TEST_KEY_BASE}-2" fcm make -C "${PWD}/loc2"
+LOG="${PWD}/loc2/fcm-make.log"
+file_grep "${TEST_KEY_BASE}-2-log-1" \
+    '\[info\]   dest:    3 \[U unchanged\]' "${LOG}"
+file_grep "${TEST_KEY_BASE}-2-log-2" \
+    '\[info\] sources: total=3, analysed=0' "${LOG}"
+file_grep "${TEST_KEY_BASE}-2-log-3" \
+    '\[info\] TOTAL     targets: modified=0, unchanged=6, failed=0' "${LOG}"
+#-------------------------------------------------------------------------------
+exit
diff --git a/t/fcm-make/46-archive-mode.t b/t/fcm-make/46-archive-mode.t
new file mode 100755
index 0000000..7e0de29
--- /dev/null
+++ b/t/fcm-make/46-archive-mode.t
@@ -0,0 +1,111 @@
+#!/bin/bash
+#-------------------------------------------------------------------------------
+# (C) British Crown Copyright 2006-15 Met Office.
+#
+# This file is part of FCM, tools for managing and building source code.
+#
+# FCM is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# FCM is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with FCM. If not, see <http://www.gnu.org/licenses/>.
+#-------------------------------------------------------------------------------
+# Tests for "fcm make --archive"
+#-------------------------------------------------------------------------------
+. "$(dirname "$0")/test_header"
+tests 11
+#-------------------------------------------------------------------------------
+# Create a repository to extract
+svnadmin create 'repos'
+T_REPOS="file://${PWD}/repos"
+mkdir 't'
+cat >'t/hello.f90' <<'__FORTRAN__'
+program hello
+use world_mod, only: world
+write(*, '(a,1x,a)') 'Hello', world
+end program hello
+__FORTRAN__
+cat >'t/world_mod.f90' <<'__FORTRAN__'
+module world_mod
+character(*), parameter :: world = 'Earth'
+end module world_mod
+__FORTRAN__
+svn import --no-auth-cache -q -m'Test' t "${T_REPOS}/hello/trunk"
+rm -r 't'
+
+# Create a fcm-make.cfg to do some extract and build
+cat >'fcm-make.cfg' <<__CFG__
+steps = extract build
+extract.ns = hello
+extract.location{primary}[hello] = ${T_REPOS}/hello
+build.target{task} = link
+build.prop{file-ext.bin} =
+__CFG__
+#-------------------------------------------------------------------------------
+TEST_KEY="${TEST_KEY_BASE}-on-new"
+run_pass "${TEST_KEY}" fcm make -a
+find '.fcm-make/cache' 'build' -type f | sort >"${TEST_KEY}.find"
+file_cmp "${TEST_KEY}.find" "${TEST_KEY}.find" <<'__FIND__'
+.fcm-make/cache/extract.tar.gz
+build/bin/hello
+build/include.tar.gz
+build/o.tar.gz
+__FIND__
+
+touch 'new'
+sleep 1
+
+TEST_KEY="${TEST_KEY_BASE}-on-incr"
+run_pass "${TEST_KEY}" fcm make -a
+find '.fcm-make/cache' 'build' -type f -newer 'new' \
+    | sort >"${TEST_KEY}.find.new"
+file_cmp "${TEST_KEY}.find.new" "${TEST_KEY}.find.new" <<'__FIND__'
+.fcm-make/cache/extract.tar.gz
+build/include.tar.gz
+build/o.tar.gz
+__FIND__
+find '.fcm-make/cache' 'build' -type f '!' -newer 'new' \
+    | sort >"${TEST_KEY}.find.old"
+file_cmp "${TEST_KEY}.find.old" "${TEST_KEY}.find.old" <<'__FIND__'
+build/bin/hello
+__FIND__
+
+TEST_KEY="${TEST_KEY_BASE}-on-incr-build-o"
+run_pass "${TEST_KEY}" \
+    fcm make -a 'build.prop{archive-ok-target-category}=o'
+find '.fcm-make/cache' 'build' -type f -newer 'new' \
+    | sort >"${TEST_KEY}.find.new"
+file_cmp "${TEST_KEY}.find.new" "${TEST_KEY}.find.new" <<'__FIND__'
+.fcm-make/cache/extract.tar.gz
+build/o.tar.gz
+__FIND__
+find '.fcm-make/cache' 'build' -type f '!' -newer 'new' \
+    | sort >"${TEST_KEY}.find.old"
+file_cmp "${TEST_KEY}.find.old" "${TEST_KEY}.find.old" <<'__FIND__'
+build/bin/hello
+build/include/world_mod.mod
+__FIND__
+
+run_pass "${TEST_KEY_BASE}-off" fcm make
+find '.fcm-make/cache' 'build' -type f -newer 'new' \
+    | sort >"${TEST_KEY}.find.new"
+file_cmp "${TEST_KEY}.find.new" "${TEST_KEY}.find.new" <'/dev/null'
+find '.fcm-make/cache' 'build' -type f '!' -newer 'new' \
+    | sort >"${TEST_KEY}.find.old"
+file_cmp "${TEST_KEY}.find.old" "${TEST_KEY}.find.old" <<'__FIND__'
+.fcm-make/cache/extract/hello/0/hello.f90
+.fcm-make/cache/extract/hello/0/world_mod.f90
+build/bin/hello
+build/include/world_mod.mod
+build/o/hello.o
+build/o/world_mod.o
+__FIND__
+#-------------------------------------------------------------------------------
+exit 0
diff --git a/t/fcm-merge/00-simple.t b/t/fcm-merge/00-simple.t
index 7e3b1d7..dbc20dc 100644
--- a/t/fcm-merge/00-simple.t
+++ b/t/fcm-merge/00-simple.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,40 +21,64 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
-tests 18
+check_svn_version
+tests 42
 #-------------------------------------------------------------------------------
 setup
 init_repos
 init_merge_branches merge1 merge2 $REPOS_URL
 cd $TEST_DIR/wc
 #-------------------------------------------------------------------------------
+# Test the various mergeinfo output before merging.
+test_mergeinfo "$TEST_KEY_BASE-pre" \
+    $ROOT_URL/branches/dev/Share/merge1 <<__RESULTS__
+begin-prop
+end-prop
+begin-info
+    youngest common ancestor
+    |         last full merge
+    |         |        tip of branch
+    |         |        |         repository path
+
+    1                  9       
+    |                  |       
+       --| |------------         branches/dev/Share/merge1
+      /                        
+     /                         
+  -------| |------------         trunk
+                       |       
+                       9       
+end-info
+begin-eligible
+r5
+end-eligible
+begin-merged
+end-merged
+__RESULTS__
+#-------------------------------------------------------------------------------
 # Tests fcm merge --dry-run
 TEST_KEY=$TEST_KEY_BASE-dry-run
 export SVN_EDITOR="sed -i 1i\foo"
 run_pass "$TEST_KEY" fcm merge --dry-run $ROOT_URL/branches/dev/Share/merge1
-if $SVN_VERSION_IS_16; then
-    START_REV=2
-else
-    START_REV=4
-fi
-file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+merge_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
 Eligible merge(s) from /${PROJECT}branches/dev/Share/merge1 at 9: 5
 --------------------------------------------------------------------------------
 Merge: /${PROJECT}branches/dev/Share/merge1 at 5
  c.f.: /${PROJECT}trunk at 1
 -------------------------------------------------------------------------dry-run
---- Merging r$START_REV through r5 into '.':
-U    subroutine/hello_sub_dummy.h
-A    added_file
+--- Merging r4 through r5 into '.':
 A    added_directory
-A    added_directory/hello_constants_dummy.inc
-A    added_directory/hello_constants.inc
 A    added_directory/hello_constants.f90
+A    added_directory/hello_constants.inc
+A    added_directory/hello_constants_dummy.inc
+A    added_file
 A    module/tree_conflict_file
-U    module/hello_constants_dummy.inc
-U    module/hello_constants.inc
-U    module/hello_constants.f90
 U    lib/python/info/poems.py
+U    module/hello_constants.f90
+U    module/hello_constants.inc
+U    module/hello_constants_dummy.inc
+U    subroutine/hello_sub_dummy.h
 -------------------------------------------------------------------------dry-run
 __OUT__
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
@@ -78,53 +102,40 @@ file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 TEST_KEY=$TEST_KEY_BASE-non-interactive
 export SVN_EDITOR="sed -i 1i\foo" 
 run_pass "$TEST_KEY" fcm merge --non-interactive $ROOT_URL/branches/dev/Share/merge1
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Eligible merge(s) from /${PROJECT}branches/dev/Share/merge1 at 9: 5
---------------------------------------------------------------------------------
-Merge: /${PROJECT}branches/dev/Share/merge1 at 5
- c.f.: /${PROJECT}trunk at 1
-Merge succeeded.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+merge_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
 Eligible merge(s) from /${PROJECT}branches/dev/Share/merge1 at 9: 5
 --------------------------------------------------------------------------------
 Merge: /${PROJECT}branches/dev/Share/merge1 at 5
  c.f.: /${PROJECT}trunk at 1
 Merge succeeded.
 --------------------------------------------------------------------------actual
---- Merging r$START_REV through r5 into '.':
-U    subroutine/hello_sub_dummy.h
-A    added_file
+--- Merging r4 through r5 into '.':
 A    added_directory
-A    added_directory/hello_constants_dummy.inc
-A    added_directory/hello_constants.inc
 A    added_directory/hello_constants.f90
+A    added_directory/hello_constants.inc
+A    added_directory/hello_constants_dummy.inc
+A    added_file
 A    module/tree_conflict_file
-U    module/hello_constants_dummy.inc
-U    module/hello_constants.inc
-U    module/hello_constants.f90
 U    lib/python/info/poems.py
---- Recording mergeinfo for merge of r$START_REV through r5 into '.':
+U    module/hello_constants.f90
+U    module/hello_constants.inc
+U    module/hello_constants_dummy.inc
+U    subroutine/hello_sub_dummy.h
+--- Recording mergeinfo for merge of r4 through r5 into '.':
  U   .
 --------------------------------------------------------------------------actual
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests svn status result of fcm merge --non-interactive
 TEST_KEY=$TEST_KEY_BASE-non-interactive-status
 run_pass "$TEST_KEY" svn status --config-dir=$TEST_DIR/.subversion/
-sort $TEST_DIR/"$TEST_KEY.out" -o $TEST_DIR/"$TEST_KEY.out"
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+status_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
  M      .
 ?       unversioned_file
 A  +    added_directory
-A  +    added_directory/hello_constants.f90
-A  +    added_directory/hello_constants.inc
-A  +    added_directory/hello_constants_dummy.inc
 A  +    added_file
 A  +    module/tree_conflict_file
 M       lib/python/info/poems.py
@@ -133,107 +144,23 @@ M       module/hello_constants.inc
 M       module/hello_constants_dummy.inc
 M       subroutine/hello_sub_dummy.h
 __OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
- M      .
-?       unversioned_file
-A  +    added_directory
-A  +    added_file
-A  +    module/tree_conflict_file
-M       lib/python/info/poems.py
-M       module/hello_constants.f90
-M       module/hello_constants.inc
-M       module/hello_constants_dummy.inc
-M       subroutine/hello_sub_dummy.h
-__OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests svn diff result of fcm merge --non-interactive
 TEST_KEY=$TEST_KEY_BASE-non-interactive-diff
 run_pass "$TEST_KEY" svn diff
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+diff_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
+
+Index: .
+===================================================================
+--- .	(revision 9)
++++ .	(working copy)
 
 Property changes on: .
 ___________________________________________________________________
 Added: svn:mergeinfo
-   Merged /${PROJECT}branches/dev/Share/merge1:r4-5
-
-Index: subroutine/hello_sub_dummy.h
-===================================================================
---- subroutine/hello_sub_dummy.h	(revision 9)
-+++ subroutine/hello_sub_dummy.h	(working copy)
-@@ -1 +1,2 @@
- #include "hello_sub.h"
-+Modified a line
-Index: module/hello_constants_dummy.inc
-===================================================================
---- module/hello_constants_dummy.inc	(revision 9)
-+++ module/hello_constants_dummy.inc	(working copy)
-@@ -1 +1 @@
--INCLUDE 'hello_constants.inc'
-+INCLUDE 'hello_constants.INc'
-Index: module/hello_constants.inc
-===================================================================
---- module/hello_constants.inc	(revision 9)
-+++ module/hello_constants.inc	(working copy)
-@@ -1 +1,2 @@
--CHARACTER (LEN=80), PARAMETER :: hello_string = 'Hello Earth!'
-+CHARACTER (
-+LEN=80), PARAMETER :: hello_strINg = 'Hello Earth!!'
-Index: module/hello_constants.f90
-===================================================================
---- module/hello_constants.f90	(revision 9)
-+++ module/hello_constants.f90	(working copy)
-@@ -1,5 +1,5 @@
- MODULE Hello_Constants
- 
--INCLUDE 'hello_constants_dummy.inc'
-+INCLUDE 'hello_constants_dummy.INc'
- 
- END MODULE Hello_Constants
-Index: lib/python/info/poems.py
-===================================================================
---- lib/python/info/poems.py	(revision 9)
-+++ lib/python/info/poems.py	(working copy)
-@@ -1,24 +1,23 @@
--#!/usr/bin/env python
--# -*- coding: utf-8 -*-
- """The Python, by Hilaire Belloc
- 
- A Python I should not advise,--
--It needs a doctor for its eyes,
-+It needs a doctor FOR its eyes,
- And has the measles yearly.
--However, if you feel inclined
--To get one (to improve your mind,
-+However, if you feel INclINed
-+To get one (
-+to improve your mINd,
- And not from fashion merely),
- Allow no music near its cage;
--And when it flies into a rage
-+And when it flies INto a rage
- Chastise it, most severely.
--I had an aunt in Yucatan
-+I had an aunt IN Yucatan
- Who bought a Python from a man
--And kept it for a pet.
-+And kept it FOR a pet.
- She died, because she never knew
- These simple little rules and few;--
--The Snake is living yet.
-+The Snake is livINg yet.
- """
- 
- import this
- 
--print "\n",  __doc__
-+prINt "\n",  __doc__
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+   Merged /branches/dev/Share/merge1:r4-5
 Index: lib/python/info/poems.py
 ===================================================================
 --- lib/python/info/poems.py	(revision 9)
@@ -305,17 +232,37 @@ Index: subroutine/hello_sub_dummy.h
 @@ -1 +1,2 @@
  #include "hello_sub.h"
 +Modified a line
-Index: .
-===================================================================
---- .	(revision 9)
-+++ .	(working copy)
-
-Property changes on: .
-___________________________________________________________________
-Added: svn:mergeinfo
-   Merged /${PROJECT}branches/dev/Share/merge1:r4-5
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
+#-------------------------------------------------------------------------------
+# Test the various mergeinfo output after merging.
+test_mergeinfo "$TEST_KEY_BASE-post" \
+    $ROOT_URL/branches/dev/Share/merge1 - <<__RESULTS__
+begin-prop
+/branches/dev/Share/merge1:4-5
+end-prop
+begin-info
+    youngest common ancestor
+    |         last full merge
+    |         |        tip of branch
+    |         |        |         repository path
+
+    1                  9       
+    |                  |       
+       --| |------------         branches/dev/Share/merge1
+      /                        
+     /                         
+  -------| |------------         trunk
+                       |       
+                       9       
+end-info
+begin-eligible
+end-eligible
+begin-merged
+r4
+r5
+end-merged
+__RESULTS__
+#-------------------------------------------------------------------------------
 teardown
 #-------------------------------------------------------------------------------
diff --git a/t/fcm-merge/01-complex.t b/t/fcm-merge/01-complex.t
index 66fb4f6..94a1985 100644
--- a/t/fcm-merge/01-complex.t
+++ b/t/fcm-merge/01-complex.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,30 +21,49 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
-tests 90
+check_svn_version
+tests 234
 #-------------------------------------------------------------------------------
 setup
 init_repos
 init_merge_branches merge1 merge2 $REPOS_URL
 export SVN_EDITOR="sed -i 1i\foo"
 cd $TEST_DIR/wc
+svn switch -q $ROOT_URL/branches/dev/Share/merge1
+#-------------------------------------------------------------------------------
+# Test the various mergeinfo output before merging.
+test_mergeinfo "$TEST_KEY_BASE-trunk-into-branch-1-pre" \
+    $ROOT_URL/trunk <<__RESULTS__
+begin-prop
+end-prop
+begin-info
+    youngest common ancestor
+    |         last full merge
+    |         |        tip of branch
+    |         |        |         repository path
+
+    1                  9       
+    |                  |       
+  -------| |------------         trunk
+     \                         
+      \                        
+       --| |------------         branches/dev/Share/merge1
+                       |       
+                       9       
+end-info
+begin-eligible
+r8
+r9
+end-eligible
+begin-merged
+end-merged
+__RESULTS__
 #-------------------------------------------------------------------------------
 # Tests fcm merge of trunk-into-branch (1)
-svn switch -q $ROOT_URL/branches/dev/Share/merge1
 TEST_KEY=$TEST_KEY_BASE-trunk-into-branch-1-non-root
 cd module
 run_pass "$TEST_KEY" fcm merge --non-interactive trunk
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-$TEST_DIR/wc: working directory changed to top of working copy.
-Eligible merge(s) from /${PROJECT}trunk at 9: 9 8
---------------------------------------------------------------------------------
-Merge: /${PROJECT}trunk at 9
- c.f.: /${PROJECT}trunk at 1
-Merge succeeded.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
 $TEST_DIR/wc: working directory changed to top of working copy.
 Eligible merge(s) from /${PROJECT}trunk at 9: 9 8
 --------------------------------------------------------------------------------
@@ -58,15 +77,14 @@ U    lib/python/info/__init__.py
  U   .
 --------------------------------------------------------------------------actual
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 cd ..
 #-------------------------------------------------------------------------------
 # Tests svn status result of fcm merge (1)
 TEST_KEY=$TEST_KEY_BASE-trunk-into-branch-1-status
 run_pass "$TEST_KEY" svn status --config-dir=$TEST_DIR/.subversion/
-sort $TEST_DIR/"$TEST_KEY.out" -o $TEST_DIR/"$TEST_KEY.out"
-file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+status_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
  M      .
 ?       unversioned_file
 M       lib/python/info/__init__.py
@@ -76,24 +94,8 @@ file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 # Tests svn diff result of fcm merge (1)
 TEST_KEY=$TEST_KEY_BASE-trunk-into-branch-1-diff
 run_pass "$TEST_KEY" svn diff
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-
-Property changes on: .
-___________________________________________________________________
-Added: svn:mergeinfo
-   Merged /${PROJECT}trunk:r2-9
-
-Index: lib/python/info/__init__.py
-===================================================================
---- lib/python/info/__init__.py	(revision 9)
-+++ lib/python/info/__init__.py	(working copy)
-@@ -0,0 +1,2 @@
-+trunk change
-+another trunk change
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+diff_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
 Index: lib/python/info/__init__.py
 ===================================================================
 --- lib/python/info/__init__.py	(revision 9)
@@ -111,7 +113,6 @@ ___________________________________________________________________
 Added: svn:mergeinfo
    Merged /${PROJECT}trunk:r2-9
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests fcm commit of fcm merge (1)
@@ -119,37 +120,7 @@ TEST_KEY=$TEST_KEY_BASE-trunk-into-branch-1-commit
 run_pass "$TEST_KEY" fcm commit <<__IN__
 y
 __IN__
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-[info] sed -i 1i\foo: starting commit message editor...
-Change summary:
---------------------------------------------------------------------------------
-[Root   : $REPOS_URL]
-[Project: ${TEST_PROJECT:-}]
-[Branch : branches/dev/Share/merge1]
-[Sub-dir: ]
-
- M      .
-M       lib/python/info/__init__.py
---------------------------------------------------------------------------------
-Commit message is as follows:
---------------------------------------------------------------------------------
-foo
-Merged into /${PROJECT}branches/dev/Share/merge1: /${PROJECT}trunk at 9 cf. /${PROJECT}trunk at 1
---------------------------------------------------------------------------------
-
-*** WARNING: YOU ARE COMMITTING TO A Share BRANCH.
-*** Please ensure that you have the owner's permission.
-
-Would you like to commit this change?
-Enter "y" or "n" (or just press <return> for "n"): Sending        .
-Sending        lib/python/info/__init__.py
-Transmitting file data .
-Committed revision 10.
-At revision 10.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
 [info] sed -i 1i\foo: starting commit message editor...
 Change summary:
 --------------------------------------------------------------------------------
@@ -178,7 +149,6 @@ Committed revision 10.
 Updating '.':
 At revision 10.
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests fcm log of fcm merge (1)
@@ -208,6 +178,35 @@ initial trunk import
 __OUT__
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
+# Test the various mergeinfo output after merging.
+test_mergeinfo "$TEST_KEY_BASE-trunk-into-branch-1-post" \
+    $ROOT_URL/trunk <<__RESULTS__
+begin-prop
+/trunk:2-9
+end-prop
+begin-info
+    youngest common ancestor
+    |         last full merge
+    |         |        tip of branch
+    |         |        |         repository path
+
+    1         9        10      
+    |         |        |       
+  -------| |------------         trunk
+     \         \               
+      \         \              
+       --| |------------         branches/dev/Share/merge1
+                       |       
+                       10      
+end-info
+begin-eligible
+end-eligible
+begin-merged
+r8
+r9
+end-merged
+__RESULTS__
+#-------------------------------------------------------------------------------
 # Tests fcm merge of branch-into-trunk (1)
 TEST_KEY=$TEST_KEY_BASE-branch-into-trunk-1
 BRANCH_MOD_FILE=$(find . -type f | sed "/\.svn/d" | sort | head -3| tail -1)
@@ -219,17 +218,40 @@ rm -rf $TEST_DIR/wc
 mkdir $TEST_DIR/wc
 svn checkout -q $ROOT_URL/trunk $TEST_DIR/wc
 cd $TEST_DIR/wc
+#-------------------------------------------------------------------------------
+# Test the various mergeinfo output before merging.
+test_mergeinfo "$TEST_KEY_BASE-branch-into-trunk-1-pre" \
+    $ROOT_URL/branches/dev/Share/merge1 <<__RESULTS__
+begin-prop
+end-prop
+begin-info
+    youngest common ancestor
+    |         last full merge
+    |         |        tip of branch
+    |         |        |         repository path
+
+    1                  11      
+    |                  |       
+       --| |------------         branches/dev/Share/merge1
+      /         /              
+     /         /               
+  -------| |------------         trunk
+              |        |       
+              9        11      
+end-info
+begin-eligible
+r5
+r10
+r11
+end-eligible
+begin-merged
+end-merged
+__RESULTS__
+#-------------------------------------------------------------------------------
+TEST_KEY=$TEST_KEY_BASE-branch-into-trunk-1
 run_pass "$TEST_KEY" fcm merge --non-interactive branches/dev/Share/merge1
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Eligible merge(s) from /${PROJECT}branches/dev/Share/merge1 at 11: 11 10
---------------------------------------------------------------------------------
-Merge: /${PROJECT}branches/dev/Share/merge1 at 11
- c.f.: /${PROJECT}trunk at 9
-Merge succeeded.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+merge_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
 Eligible merge(s) from /${PROJECT}branches/dev/Share/merge1 at 11: 11 10
 --------------------------------------------------------------------------------
 Merge: /${PROJECT}branches/dev/Share/merge1 at 11
@@ -237,142 +259,55 @@ Merge: /${PROJECT}branches/dev/Share/merge1 at 11
 Merge succeeded.
 --------------------------------------------------------------------------actual
 --- Merging differences between repository URLs into '.':
-U    subroutine/hello_sub_dummy.h
-A    added_file
 A    added_directory
-A    added_directory/hello_constants_dummy.inc
-A    added_directory/hello_constants.inc
 A    added_directory/hello_constants.f90
+A    added_directory/hello_constants.inc
+A    added_directory/hello_constants_dummy.inc
+A    added_file
 A    module/tree_conflict_file
-U    module/hello_constants_dummy.inc
-U    module/hello_constants.inc
-U    module/hello_constants.f90
 U    lib/python/info/poems.py
+U    module/hello_constants.f90
+U    module/hello_constants.inc
+U    module/hello_constants_dummy.inc
+U    subroutine/hello_sub_dummy.h
 --- Recording mergeinfo for merge between repository URLs into '.':
  U   .
 --------------------------------------------------------------------------actual
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests svn status result of fcm merge (1)
 TEST_KEY=$TEST_KEY_BASE-branch-into-trunk-1-status
 run_pass "$TEST_KEY" svn status --config-dir=$TEST_DIR/.subversion/
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
- M      .
-M       subroutine/hello_sub_dummy.h
-A  +    added_file
-A  +    module/tree_conflict_file
-M       module/hello_constants_dummy.inc
-M       module/hello_constants.inc
-M       module/hello_constants.f90
-A  +    added_directory
-A  +    added_directory/hello_constants_dummy.inc
-A  +    added_directory/hello_constants.inc
-A  +    added_directory/hello_constants.f90
-M       lib/python/info/poems.py
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+status_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
  M      .
 A  +    added_directory
 A  +    added_file
+A  +    module/tree_conflict_file
 M       lib/python/info/poems.py
 M       module/hello_constants.f90
 M       module/hello_constants.inc
 M       module/hello_constants_dummy.inc
-A  +    module/tree_conflict_file
 M       subroutine/hello_sub_dummy.h
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests svn diff result of fcm merge (1)
 TEST_KEY=$TEST_KEY_BASE-branch-into-trunk-1-diff
 run_pass "$TEST_KEY" svn diff
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+diff_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
+
+Index: .
+===================================================================
+--- .	(revision 11)
++++ .	(working copy)
 
 Property changes on: .
 ___________________________________________________________________
 Added: svn:mergeinfo
-   Merged /${PROJECT}branches/dev/Share/merge1:r2-11
-
-Index: subroutine/hello_sub_dummy.h
-===================================================================
---- subroutine/hello_sub_dummy.h	(revision 11)
-+++ subroutine/hello_sub_dummy.h	(working copy)
-@@ -1 +1,2 @@
- #include "hello_sub.h"
-+Modified a line
-Index: module/hello_constants_dummy.inc
-===================================================================
---- module/hello_constants_dummy.inc	(revision 11)
-+++ module/hello_constants_dummy.inc	(working copy)
-@@ -1 +1 @@
--INCLUDE 'hello_constants.inc'
-+INCLUDE 'hello_constants.INc'
-Index: module/hello_constants.inc
-===================================================================
---- module/hello_constants.inc	(revision 11)
-+++ module/hello_constants.inc	(working copy)
-@@ -1 +1,2 @@
--CHARACTER (LEN=80), PARAMETER :: hello_string = 'Hello Earth!'
-+CHARACTER (
-+LEN=80), PARAMETER :: hello_strINg = 'Hello Earth!!'
-Index: module/hello_constants.f90
-===================================================================
---- module/hello_constants.f90	(revision 11)
-+++ module/hello_constants.f90	(working copy)
-@@ -1,5 +1,5 @@
- MODULE Hello_Constants
- 
--INCLUDE 'hello_constants_dummy.inc'
-+INCLUDE 'hello_constants_dummy.INc'
- 
- END MODULE Hello_Constants
-Index: lib/python/info/poems.py
-===================================================================
---- lib/python/info/poems.py	(revision 11)
-+++ lib/python/info/poems.py	(working copy)
-@@ -1,24 +1,23 @@
--#!/usr/bin/env python
--# -*- coding: utf-8 -*-
- """The Python, by Hilaire Belloc
- 
- A Python I should not advise,--
--It needs a doctor for its eyes,
-+It needs a doctor FOR its eyes,
- And has the measles yearly.
--However, if you feel inclined
--To get one (to improve your mind,
-+However, if you feel INclINed
-+To get one (
-+to improve your mINd,
- And not from fashion merely),
- Allow no music near its cage;
--And when it flies into a rage
-+And when it flies INto a rage
- Chastise it, most severely.
--I had an aunt in Yucatan
-+I had an aunt IN Yucatan
- Who bought a Python from a man
--And kept it for a pet.
-+And kept it FOR a pet.
- She died, because she never knew
- These simple little rules and few;--
--The Snake is living yet.
-+The Snake is livINg yet.
- """
- 
- import this
- 
--print "\n",  __doc__
-+prINt "\n",  __doc__
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+   Merged /${PROJECT}branches/dev/Share/merge1:r4-11
 Index: lib/python/info/poems.py
 ===================================================================
 --- lib/python/info/poems.py	(revision 11)
@@ -444,17 +379,7 @@ Index: subroutine/hello_sub_dummy.h
 @@ -1 +1,2 @@
  #include "hello_sub.h"
 +Modified a line
-Index: .
-===================================================================
---- .	(revision 11)
-+++ .	(working copy)
-
-Property changes on: .
-___________________________________________________________________
-Added: svn:mergeinfo
-   Merged /${PROJECT}branches/dev/Share/merge1:r4-11
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests fcm commit of fcm merge (1)
@@ -462,57 +387,8 @@ TEST_KEY=$TEST_KEY_BASE-branch-into-trunk-1-commit
 run_pass "$TEST_KEY" fcm commit <<__IN__
 y
 __IN__
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-[info] sed -i 1i\foo: starting commit message editor...
-Change summary:
---------------------------------------------------------------------------------
-[Root   : $REPOS_URL]
-[Project: ${TEST_PROJECT:-}]
-[Branch : trunk]
-[Sub-dir: ]
-
- M      .
-M       subroutine/hello_sub_dummy.h
-A  +    added_file
-A  +    module/tree_conflict_file
-M       module/hello_constants_dummy.inc
-M       module/hello_constants.inc
-M       module/hello_constants.f90
-A  +    added_directory
-A  +    added_directory/hello_constants_dummy.inc
-A  +    added_directory/hello_constants.inc
-A  +    added_directory/hello_constants.f90
-M       lib/python/info/poems.py
---------------------------------------------------------------------------------
-Commit message is as follows:
---------------------------------------------------------------------------------
-foo
-Merged into /${PROJECT}trunk: /${PROJECT}branches/dev/Share/merge1 at 11 cf. /${PROJECT}trunk at 9
---------------------------------------------------------------------------------
-
-*** WARNING: YOU ARE COMMITTING TO THE TRUNK.
-*** Please ensure that your change conforms to your project's working practices.
-
-Would you like to commit this change?
-Enter "y" or "n" (or just press <return> for "n"): Sending        .
-Adding         added_directory
-Adding         added_directory/hello_constants.f90
-Adding         added_directory/hello_constants.inc
-Adding         added_directory/hello_constants_dummy.inc
-Adding         added_file
-Sending        lib/python/info/poems.py
-Sending        module/hello_constants.f90
-Sending        module/hello_constants.inc
-Sending        module/hello_constants_dummy.inc
-Adding         module/tree_conflict_file
-Sending        subroutine/hello_sub_dummy.h
-Transmitting file data .....
-Committed revision 12.
-At revision 12.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+commit_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
 [info] sed -i 1i\foo: starting commit message editor...
 Change summary:
 --------------------------------------------------------------------------------
@@ -524,11 +400,11 @@ Change summary:
  M      .
 A  +    added_directory
 A  +    added_file
+A  +    module/tree_conflict_file
 M       lib/python/info/poems.py
 M       module/hello_constants.f90
 M       module/hello_constants.inc
 M       module/hello_constants_dummy.inc
-A  +    module/tree_conflict_file
 M       subroutine/hello_sub_dummy.h
 --------------------------------------------------------------------------------
 Commit message is as follows:
@@ -544,18 +420,17 @@ Would you like to commit this change?
 Enter "y" or "n" (or just press <return> for "n"): Sending        .
 Adding         added_directory
 Adding         added_file
+Adding         module/tree_conflict_file
 Sending        lib/python/info/poems.py
 Sending        module/hello_constants.f90
 Sending        module/hello_constants.inc
 Sending        module/hello_constants_dummy.inc
-Adding         module/tree_conflict_file
 Sending        subroutine/hello_sub_dummy.h
 Transmitting file data .....
 Committed revision 12.
 Updating '.':
 At revision 12.
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests fcm log of fcm merge branch-into-trunk (1)
@@ -585,26 +460,84 @@ initial trunk import
 __OUT__
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
+# Test the various mergeinfo output after merging.
+test_mergeinfo "$TEST_KEY_BASE-branch-into-trunk-1-post" \
+    $ROOT_URL/branches/dev/Share/merge1 <<__RESULTS__
+begin-prop
+/branches/dev/Share/merge1:4-11
+end-prop
+begin-info
+    youngest common ancestor
+    |         last full merge
+    |         |        tip of branch
+    |         |        |         repository path
+
+    1         11       12      
+    |         |        |       
+       --| |------------         branches/dev/Share/merge1
+      /        \               
+     /          \              
+  -------| |------------         trunk
+                       |       
+                       12      
+end-info
+begin-eligible
+end-eligible
+begin-merged
+r4
+r5
+r10
+r11
+end-merged
+__RESULTS__
+#-------------------------------------------------------------------------------
 # Tests fcm merge of branch-into-trunk (2)
 svn switch -q $ROOT_URL/branches/dev/Share/merge1
 MOD_FILE=$(find . -type f | sed "/\.svn/d" | sort | head -4 | tail -1)
 echo "call_extra_feature()" >>$MOD_FILE
 svn commit -q -m "Made branch change to add extra feature"
 svn update -q
+# Create a new branch to up the revision number, as a test.
+init_branch merge3 $REPOS_URL
+# Checkout the trunk.
 svn switch -q $ROOT_URL/trunk
+#-------------------------------------------------------------------------------
+# Test the various mergeinfo output before merging.
+test_mergeinfo "$TEST_KEY_BASE-branch-into-trunk-2-pre" \
+    $ROOT_URL/branches/dev/Share/merge1 <<__RESULTS__
+begin-prop
+/branches/dev/Share/merge1:4-11
+end-prop
+begin-info
+    youngest common ancestor
+    |         last full merge
+    |         |        tip of branch
+    |         |        |         repository path
+
+    1         11       14      
+    |         |        |       
+       --| |------------         branches/dev/Share/merge1
+      /        \               
+     /          \              
+  -------| |------------         trunk
+                       |       
+                       14      
+end-info
+begin-eligible
+r13
+end-eligible
+begin-merged
+r4
+r5
+r10
+r11
+end-merged
+__RESULTS__
+#-------------------------------------------------------------------------------
 TEST_KEY=$TEST_KEY_BASE-branch-into-trunk-2
 run_pass "$TEST_KEY" fcm merge --non-interactive branches/dev/Share/merge1
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Eligible merge(s) from /${PROJECT}branches/dev/Share/merge1 at 13: 13
---------------------------------------------------------------------------------
-Merge: /${PROJECT}branches/dev/Share/merge1 at 13
- c.f.: /${PROJECT}branches/dev/Share/merge1 at 11
-Merge succeeded.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Eligible merge(s) from /${PROJECT}branches/dev/Share/merge1 at 13: 13
+file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+Eligible merge(s) from /${PROJECT}branches/dev/Share/merge1 at 14: 13
 --------------------------------------------------------------------------------
 Merge: /${PROJECT}branches/dev/Share/merge1 at 13
  c.f.: /${PROJECT}branches/dev/Share/merge1 at 11
@@ -616,7 +549,6 @@ U    added_file
  U   .
 --------------------------------------------------------------------------actual
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests svn status result of fcm merge branch-into-trunk (2)
@@ -631,42 +563,26 @@ file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 # Tests svn diff result of fcm merge branch-into-trunk (2)
 TEST_KEY=$TEST_KEY_BASE-branch-into-trunk-2-diff
 run_pass "$TEST_KEY" svn diff
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+diff_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
+
+Index: .
+===================================================================
+--- .	(revision 14)
++++ .	(working copy)
 
 Property changes on: .
 ___________________________________________________________________
 Modified: svn:mergeinfo
    Merged /${PROJECT}branches/dev/Share/merge1:r12-13
-
 Index: added_file
 ===================================================================
---- added_file	(revision 13)
+--- added_file	(revision 14)
 +++ added_file	(working copy)
 @@ -1 +1,2 @@
  INCLUDE 'hello_constants.INc'
 +call_extra_feature()
 __OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Index: added_file
-===================================================================
---- added_file	(revision 13)
-+++ added_file	(working copy)
-@@ -1 +1,2 @@
- INCLUDE 'hello_constants.INc'
-+call_extra_feature()
-Index: .
-===================================================================
---- .	(revision 13)
-+++ .	(working copy)
-
-Property changes on: .
-___________________________________________________________________
-Modified: svn:mergeinfo
-   Merged /${PROJECT}branches/dev/Share/merge1:r12-13
-__OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests fcm commit of fcm merge branch-into-trunk (2)
@@ -700,8 +616,8 @@ Would you like to commit this change?
 Enter "y" or "n" (or just press <return> for "n"): Sending        .
 Sending        added_file
 Transmitting file data .
-Committed revision 14.
-At revision 14.
+Committed revision 15.
+At revision 15.
 __OUT__
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
@@ -711,7 +627,7 @@ run_pass "$TEST_KEY" fcm log
 sed -i "s/\(.*|.*|\).*\(|.*\)$/\1 date \2/g" $TEST_DIR/$TEST_KEY.out
 file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
 ------------------------------------------------------------------------
-r14 | $LOGNAME | date | 3 lines
+r15 | $LOGNAME | date | 3 lines
 
 foo
 Merged into /${PROJECT}trunk: /${PROJECT}branches/dev/Share/merge1 at 13 cf. /${PROJECT}branches/dev/Share/merge1 at 11
@@ -738,29 +654,86 @@ initial trunk import
 __OUT__
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
+# Test the various mergeinfo output after merging.
+test_mergeinfo "$TEST_KEY_BASE-branch-into-trunk-2-post" \
+    $ROOT_URL/branches/dev/Share/merge1 <<__RESULTS__
+begin-prop
+/branches/dev/Share/merge1:4-13
+end-prop
+begin-info
+    youngest common ancestor
+    |         last full merge
+    |         |        tip of branch
+    |         |        |         repository path
+
+    1         13       15      
+    |         |        |       
+       --| |------------         branches/dev/Share/merge1
+      /        \               
+     /          \              
+  -------| |------------         trunk
+                       |       
+                       15      
+end-info
+begin-eligible
+end-eligible
+begin-merged
+r4
+r5
+r10
+r11
+r13
+end-merged
+__RESULTS__
+#-------------------------------------------------------------------------------
 # Tests fcm merge of trunk-into-branch (2)
 echo "# trunk modification" >>$MOD_FILE
 svn commit -q -m "Made trunk change - a simple edit of $MOD_FILE"
 svn update -q
 svn switch -q $ROOT_URL/branches/dev/Share/merge1
-TEST_KEY=$TEST_KEY_BASE-trunk-into-branch-2
+
 echo "# added another line for simple repeat testing" >>$BRANCH_MOD_FILE
 svn commit -q -m "Made branch change for merge repeat test"
 svn update -q
+#------------------------------------------------------------------------------
+# Test the various mergeinfo output before merging.
+test_mergeinfo "$TEST_KEY_BASE-trunk-into-branch-2-pre" \
+    $ROOT_URL/trunk <<__RESULTS__
+begin-prop
+/trunk:2-9
+end-prop
+begin-info
+    youngest common ancestor
+    |         last full merge
+    |         |        tip of branch
+    |         |        |         repository path
+
+    1                  17      
+    |                  |       
+  -------| |------------         trunk
+     \          /              
+      \        /               
+       --| |------------         branches/dev/Share/merge1
+              |        |       
+              13       17      
+end-info
+begin-eligible
+r12
+r15
+r16
+end-eligible
+begin-merged
+r8
+r9
+end-merged
+__RESULTS__
+#------------------------------------------------------------------------------
+TEST_KEY=$TEST_KEY_BASE-trunk-into-branch-2
 run_pass "$TEST_KEY" fcm merge --non-interactive trunk
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Eligible merge(s) from /${PROJECT}trunk at 16: 15 14
---------------------------------------------------------------------------------
-Merge: /${PROJECT}trunk at 15
- c.f.: /${PROJECT}branches/dev/Share/merge1 at 13
-Merge succeeded.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Eligible merge(s) from /${PROJECT}trunk at 16: 15 14
+file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+Eligible merge(s) from /${PROJECT}trunk at 17: 16 15
 --------------------------------------------------------------------------------
-Merge: /${PROJECT}trunk at 15
+Merge: /${PROJECT}trunk at 16
  c.f.: /${PROJECT}branches/dev/Share/merge1 at 13
 Merge succeeded.
 --------------------------------------------------------------------------actual
@@ -770,7 +743,6 @@ U    added_file
  U   .
 --------------------------------------------------------------------------actual
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests svn status result of fcm merge trunk-into-branch (2)
@@ -780,50 +752,32 @@ file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
  M      .
 M       added_file
 __OUT__
-file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
-#-------------------------------------------------------------------------------
-# Tests svn diff result of fcm merge trunk-into-branch (2)
-TEST_KEY=$TEST_KEY_BASE-trunk-into-branch-2-diff
-run_pass "$TEST_KEY" svn diff
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-
-Property changes on: .
-___________________________________________________________________
-Modified: svn:mergeinfo
-   Merged /${PROJECT}trunk:r10-15
-   Merged /${PROJECT}branches/dev/Share/merge1:r2-3
-
-Index: added_file
-===================================================================
---- added_file	(revision 16)
-+++ added_file	(working copy)
-@@ -1,2 +1,3 @@
- INCLUDE 'hello_constants.INc'
- call_extra_feature()
-+# trunk modification
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Index: added_file
-===================================================================
---- added_file	(revision 16)
-+++ added_file	(working copy)
-@@ -1,2 +1,3 @@
- INCLUDE 'hello_constants.INc'
- call_extra_feature()
-+# trunk modification
+file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
+#-------------------------------------------------------------------------------
+# Tests svn diff result of fcm merge trunk-into-branch (2)
+TEST_KEY=$TEST_KEY_BASE-trunk-into-branch-2-diff
+run_pass "$TEST_KEY" svn diff
+diff_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
+
 Index: .
 ===================================================================
---- .	(revision 16)
+--- .	(revision 17)
 +++ .	(working copy)
 
 Property changes on: .
 ___________________________________________________________________
 Modified: svn:mergeinfo
-   Merged /${PROJECT}trunk:r10-15
+   Merged /${PROJECT}trunk:r10-16
+Index: added_file
+===================================================================
+--- added_file	(revision 17)
++++ added_file	(working copy)
+@@ -1,2 +1,3 @@
+ INCLUDE 'hello_constants.INc'
+ call_extra_feature()
++# trunk modification
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests fcm commit of fcm merge trunk-into-branch (2)
@@ -847,7 +801,7 @@ M       added_file
 Commit message is as follows:
 --------------------------------------------------------------------------------
 foo
-Merged into /${PROJECT}branches/dev/Share/merge1: /${PROJECT}trunk at 15 cf. /${PROJECT}branches/dev/Share/merge1 at 13
+Merged into /${PROJECT}branches/dev/Share/merge1: /${PROJECT}trunk at 16 cf. /${PROJECT}branches/dev/Share/merge1 at 13
 --------------------------------------------------------------------------------
 
 *** WARNING: YOU ARE COMMITTING TO A Share BRANCH.
@@ -857,8 +811,8 @@ Would you like to commit this change?
 Enter "y" or "n" (or just press <return> for "n"): Sending        .
 Sending        added_file
 Transmitting file data .
-Committed revision 17.
-At revision 17.
+Committed revision 18.
+At revision 18.
 __OUT__
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
@@ -868,13 +822,13 @@ run_pass "$TEST_KEY" fcm log
 sed -i "s/\(.*|.*|\).*\(|.*\)$/\1 date \2/g" $TEST_DIR/$TEST_KEY.out
 file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
 ------------------------------------------------------------------------
-r17 | $LOGNAME | date | 3 lines
+r18 | $LOGNAME | date | 3 lines
 
 foo
-Merged into /${PROJECT}branches/dev/Share/merge1: /${PROJECT}trunk at 15 cf. /${PROJECT}branches/dev/Share/merge1 at 13
+Merged into /${PROJECT}branches/dev/Share/merge1: /${PROJECT}trunk at 16 cf. /${PROJECT}branches/dev/Share/merge1 at 13
 
 ------------------------------------------------------------------------
-r16 | $LOGNAME | date | 1 line
+r17 | $LOGNAME | date | 1 line
 
 Made branch change for merge repeat test
 ------------------------------------------------------------------------
@@ -907,28 +861,87 @@ initial trunk import
 __OUT__
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
+# Test the various mergeinfo output after merging.
+test_mergeinfo "$TEST_KEY_BASE-trunk-into-branch-2-post" \
+    $ROOT_URL/trunk <<__RESULTS__
+begin-prop
+/trunk:2-16
+end-prop
+begin-info
+    youngest common ancestor
+    |         last full merge
+    |         |        tip of branch
+    |         |        |         repository path
+
+    1         16       18      
+    |         |        |       
+  -------| |------------         trunk
+     \         \               
+      \         \              
+       --| |------------         branches/dev/Share/merge1
+                       |       
+                       18      
+end-info
+begin-eligible
+end-eligible
+begin-merged
+r8
+r9
+r12
+r15
+r16
+end-merged
+__RESULTS__
+#-------------------------------------------------------------------------------
 # Tests fcm merge of branch-into-trunk (3)
 svn delete -q $BRANCH_MOD_FILE
 svn copy -q $MOD_FILE $MOD_FILE.add
 svn commit -q -m "Made branch change - deleted $BRANCH_MOD_FILE, copied $MOD_FILE"
 svn update -q
 svn switch -q $ROOT_URL/trunk
+#-------------------------------------------------------------------------------
+# Test the various mergeinfo output before merging.
+test_mergeinfo "$TEST_KEY_BASE-branch-into-trunk-3-pre" \
+    $ROOT_URL/branches/dev/Share/merge1 <<__RESULTS__
+begin-prop
+/branches/dev/Share/merge1:4-13
+end-prop
+begin-info
+    youngest common ancestor
+    |         last full merge
+    |         |        tip of branch
+    |         |        |         repository path
+
+    1                  19      
+    |                  |       
+       --| |------------         branches/dev/Share/merge1
+      /         /              
+     /         /               
+  -------| |------------         trunk
+              |        |       
+              16       19      
+end-info
+begin-eligible
+r17
+r18
+r19
+end-eligible
+begin-merged
+r4
+r5
+r10
+r11
+r13
+end-merged
+__RESULTS__
+#-------------------------------------------------------------------------------
 TEST_KEY=$TEST_KEY_BASE-branch-into-trunk-3
 run_pass "$TEST_KEY" fcm merge --non-interactive branches/dev/Share/merge1
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Eligible merge(s) from /${PROJECT}branches/dev/Share/merge1 at 18: 18 17
---------------------------------------------------------------------------------
-Merge: /${PROJECT}branches/dev/Share/merge1 at 18
- c.f.: /${PROJECT}trunk at 15
-Merge succeeded.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Eligible merge(s) from /${PROJECT}branches/dev/Share/merge1 at 18: 18 17
+file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+Eligible merge(s) from /${PROJECT}branches/dev/Share/merge1 at 19: 19 18
 --------------------------------------------------------------------------------
-Merge: /${PROJECT}branches/dev/Share/merge1 at 18
- c.f.: /${PROJECT}trunk at 15
+Merge: /${PROJECT}branches/dev/Share/merge1 at 19
+ c.f.: /${PROJECT}trunk at 16
 Merge succeeded.
 --------------------------------------------------------------------------actual
 --- Merging differences between repository URLs into '.':
@@ -938,7 +951,6 @@ A    added_file.add
  U   .
 --------------------------------------------------------------------------actual
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests svn status result of fcm merge branch-into-trunk (3)
@@ -954,42 +966,26 @@ file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 # Tests svn diff result of fcm merge branch-into-trunk (3)
 TEST_KEY=$TEST_KEY_BASE-branch-into-trunk-3-diff
 run_pass "$TEST_KEY" svn diff
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+diff_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
+
+Index: .
+===================================================================
+--- .	(revision 19)
++++ .	(working copy)
 
 Property changes on: .
 ___________________________________________________________________
 Modified: svn:mergeinfo
-   Merged /${PROJECT}branches/dev/Share/merge1:r14-18
-
-Index: added_directory/hello_constants_dummy.inc
-===================================================================
---- added_directory/hello_constants_dummy.inc	(revision 18)
-+++ added_directory/hello_constants_dummy.inc	(working copy)
-@@ -1,2 +0,0 @@
--INCLUDE 'hello_constants.INc'
--# added this line for simple repeat testing
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+   Merged /${PROJECT}branches/dev/Share/merge1:r14-19
 Index: added_directory/hello_constants_dummy.inc
 ===================================================================
---- added_directory/hello_constants_dummy.inc	(revision 18)
+--- added_directory/hello_constants_dummy.inc	(revision 19)
 +++ added_directory/hello_constants_dummy.inc	(working copy)
 @@ -1,2 +0,0 @@
 -INCLUDE 'hello_constants.INc'
 -# added this line for simple repeat testing
-Index: .
-===================================================================
---- .	(revision 18)
-+++ .	(working copy)
-
-Property changes on: .
-___________________________________________________________________
-Modified: svn:mergeinfo
-   Merged /${PROJECT}branches/dev/Share/merge1:r14-18
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests fcm commit of fcm merge branch-into-trunk (3)
@@ -998,7 +994,8 @@ run_pass "$TEST_KEY" fcm commit <<__IN__
 y
 __IN__
 sed -i "/^Updating '.':$/d" $TEST_DIR/"$TEST_KEY.out"
-file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+commit_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
 [info] sed -i 1i\foo: starting commit message editor...
 Change summary:
 --------------------------------------------------------------------------------
@@ -1008,13 +1005,13 @@ Change summary:
 [Sub-dir: ]
 
  M      .
-D       added_directory/hello_constants_dummy.inc
 A  +    added_file.add
+D       added_directory/hello_constants_dummy.inc
 --------------------------------------------------------------------------------
 Commit message is as follows:
 --------------------------------------------------------------------------------
 foo
-Merged into /${PROJECT}trunk: /${PROJECT}branches/dev/Share/merge1 at 18 cf. /${PROJECT}trunk at 15
+Merged into /${PROJECT}trunk: /${PROJECT}branches/dev/Share/merge1 at 19 cf. /${PROJECT}trunk at 16
 --------------------------------------------------------------------------------
 
 *** WARNING: YOU ARE COMMITTING TO THE TRUNK.
@@ -1022,11 +1019,11 @@ Merged into /${PROJECT}trunk: /${PROJECT}branches/dev/Share/merge1 at 18 cf. /${PRO
 
 Would you like to commit this change?
 Enter "y" or "n" (or just press <return> for "n"): Sending        .
-Deleting       added_directory/hello_constants_dummy.inc
 Adding         added_file.add
+Deleting       added_directory/hello_constants_dummy.inc
 
-Committed revision 19.
-At revision 19.
+Committed revision 20.
+At revision 20.
 __OUT__
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
@@ -1036,36 +1033,40 @@ run_pass "$TEST_KEY" fcm log $ROOT_URL
 sed -i "s/\(.*|.*|\).*\(|.*\)$/\1 date \2/g" $TEST_DIR/$TEST_KEY.out
 file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
 ------------------------------------------------------------------------
-r19 | $LOGNAME | date | 3 lines
+r20 | $LOGNAME | date | 3 lines
 
 foo
-Merged into /${PROJECT}trunk: /${PROJECT}branches/dev/Share/merge1 at 18 cf. /${PROJECT}trunk at 15
+Merged into /${PROJECT}trunk: /${PROJECT}branches/dev/Share/merge1 at 19 cf. /${PROJECT}trunk at 16
 
 ------------------------------------------------------------------------
-r18 | $LOGNAME | date | 1 line
+r19 | $LOGNAME | date | 1 line
 
 Made branch change - deleted ./added_directory/hello_constants_dummy.inc, copied ./added_file
 ------------------------------------------------------------------------
-r17 | $LOGNAME | date | 3 lines
+r18 | $LOGNAME | date | 3 lines
 
 foo
-Merged into /${PROJECT}branches/dev/Share/merge1: /${PROJECT}trunk at 15 cf. /${PROJECT}branches/dev/Share/merge1 at 13
+Merged into /${PROJECT}branches/dev/Share/merge1: /${PROJECT}trunk at 16 cf. /${PROJECT}branches/dev/Share/merge1 at 13
 
 ------------------------------------------------------------------------
-r16 | $LOGNAME | date | 1 line
+r17 | $LOGNAME | date | 1 line
 
 Made branch change for merge repeat test
 ------------------------------------------------------------------------
-r15 | $LOGNAME | date | 1 line
+r16 | $LOGNAME | date | 1 line
 
 Made trunk change - a simple edit of ./added_file
 ------------------------------------------------------------------------
-r14 | $LOGNAME | date | 3 lines
+r15 | $LOGNAME | date | 3 lines
 
 foo
 Merged into /${PROJECT}trunk: /${PROJECT}branches/dev/Share/merge1 at 13 cf. /${PROJECT}branches/dev/Share/merge1 at 11
 
 ------------------------------------------------------------------------
+r14 | $LOGNAME | date | 1 line
+
+Made a branch Created /branches/dev/Share/merge3 from /trunk at 1.
+------------------------------------------------------------------------
 r13 | $LOGNAME | date | 1 line
 
 Made branch change to add extra feature
@@ -1125,8 +1126,42 @@ initial trunk import
 __OUT__
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
+# Test the various mergeinfo output after merging.
+test_mergeinfo "$TEST_KEY_BASE-branch-into-trunk-3-post" \
+    $ROOT_URL/branches/dev/Share/merge1 <<__RESULTS__
+begin-prop
+/branches/dev/Share/merge1:4-19
+end-prop
+begin-info
+    youngest common ancestor
+    |         last full merge
+    |         |        tip of branch
+    |         |        |         repository path
+
+    1         19       20      
+    |         |        |       
+       --| |------------         branches/dev/Share/merge1
+      /        \               
+     /          \              
+  -------| |------------         trunk
+                       |       
+                       20      
+end-info
+begin-eligible
+end-eligible
+begin-merged
+r4
+r5
+r10
+r11
+r13
+r17
+r18
+r19
+end-merged
+__RESULTS__
+#-------------------------------------------------------------------------------
 # Tests fcm merge of branch-into-branch (1)
-TEST_KEY=$TEST_KEY_BASE-branch-into-branch-1
 cd $TEST_DIR
 rm -rf $TEST_DIR/wc
 mkdir $TEST_DIR/wc
@@ -1136,220 +1171,134 @@ BRANCH_2_MOD_FILE=$(find . -type f | sed "/\.svn/d" | sort | head -3| tail -1)
 echo "Second branch change" >>$BRANCH_2_MOD_FILE
 svn commit -q -m "Made branch change - added to $BRANCH_2_MOD_FILE"
 svn update -q
+#------------------------------------------------------------------------------
+# Test the various mergeinfo output before merging.
+test_mergeinfo "$TEST_KEY_BASE-branch-into-branch-1-pre" \
+    $ROOT_URL/branches/dev/Share/merge1 <<__RESULTS__
+begin-prop
+end-prop
+begin-info
+    youngest common ancestor
+    |         last full merge
+    |         |        tip of branch
+    |         |        |         repository path
+
+    1                  21      
+    |                  |       
+       --| |------------         branches/dev/Share/merge1
+  ... /                        
+      \                        
+       --| |------------         branches/dev/Share/merge2
+                       |       
+                       21      
+end-info
+begin-eligible
+r5
+r10
+r11
+r13
+r17
+r18
+r19
+end-eligible
+begin-merged
+end-merged
+__RESULTS__
+#------------------------------------------------------------------------------
+TEST_KEY=$TEST_KEY_BASE-branch-into-branch-1
 run_pass "$TEST_KEY" fcm merge $ROOT_URL/branches/dev/Share/merge1 <<__IN__
 13
 y
 __IN__
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Eligible merge(s) from /${PROJECT}branches/dev/Share/merge1 at 20: 18 17 16 13 11 10 5
-Enter a revision (or just press <return> for "18"): --------------------------------------------------------------------------------
-Merge: /${PROJECT}branches/dev/Share/merge1 at 13
- c.f.: /${PROJECT}trunk at 1
--------------------------------------------------------------------------dry-run
---- Merging r2 through r13 into '.':
-U    subroutine/hello_sub_dummy.h
-A    added_file
-A    added_directory
-A    added_directory/hello_constants_dummy.inc
-A    added_directory/hello_constants.inc
-A    added_directory/hello_constants.f90
-A    module/tree_conflict_file
-U    module/hello_constants_dummy.inc
-U    module/hello_constants.inc
-U    module/hello_constants.f90
-U    lib/python/info/__init__.py
-U    lib/python/info/poems.py
- U   .
--------------------------------------------------------------------------dry-run
-Would you like to go ahead with the merge?
-Enter "y" or "n" (or just press <return> for "n"): Merge succeeded.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-Eligible merge(s) from /${PROJECT}branches/dev/Share/merge1 at 20: 18 17 16 13 11 10 5
-Enter a revision (or just press <return> for "18"): --------------------------------------------------------------------------------
+merge_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
+Eligible merge(s) from /${PROJECT}branches/dev/Share/merge1 at 21: 19 18 17 13 11 10 5
+Enter a revision (or just press <return> for "19"): --------------------------------------------------------------------------------
 Merge: /${PROJECT}branches/dev/Share/merge1 at 13
  c.f.: /${PROJECT}trunk at 1
 -------------------------------------------------------------------------dry-run
 --- Merging r4 through r13 into '.':
-U    subroutine/hello_sub_dummy.h
-A    added_file
+ U   .
 A    added_directory
-A    added_directory/hello_constants_dummy.inc
-A    added_directory/hello_constants.inc
 A    added_directory/hello_constants.f90
+A    added_directory/hello_constants.inc
+A    added_directory/hello_constants_dummy.inc
+A    added_file
 A    module/tree_conflict_file
-U    module/hello_constants_dummy.inc
-U    module/hello_constants.inc
-U    module/hello_constants.f90
 U    lib/python/info/__init__.py
 U    lib/python/info/poems.py
- U   .
+U    module/hello_constants.f90
+U    module/hello_constants.inc
+U    module/hello_constants_dummy.inc
+U    subroutine/hello_sub_dummy.h
 -------------------------------------------------------------------------dry-run
 Would you like to go ahead with the merge?
 Enter "y" or "n" (or just press <return> for "n"): Merge succeeded.
 --------------------------------------------------------------------------actual
 --- Merging r4 through r13 into '.':
-U    subroutine/hello_sub_dummy.h
-A    added_file
+ U   .
 A    added_directory
-A    added_directory/hello_constants_dummy.inc
-A    added_directory/hello_constants.inc
 A    added_directory/hello_constants.f90
+A    added_directory/hello_constants.inc
+A    added_directory/hello_constants_dummy.inc
+A    added_file
 A    module/tree_conflict_file
-U    module/hello_constants_dummy.inc
-U    module/hello_constants.inc
-U    module/hello_constants.f90
 U    lib/python/info/__init__.py
 U    lib/python/info/poems.py
- U   .
+U    module/hello_constants.f90
+U    module/hello_constants.inc
+U    module/hello_constants_dummy.inc
+U    subroutine/hello_sub_dummy.h
 --- Recording mergeinfo for merge of r4 through r13 into '.':
  G   .
 --------------------------------------------------------------------------actual
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests svn status result of fcm merge branch-into-branch (1)
 TEST_KEY=$TEST_KEY_BASE-branch-into-branch-1-status
 run_pass "$TEST_KEY" svn status --config-dir=$TEST_DIR/.subversion/
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
- M      .
-M       subroutine/hello_sub_dummy.h
-A  +    added_file
-A  +    module/tree_conflict_file
-M       module/hello_constants_dummy.inc
-M       module/hello_constants.inc
-M       module/hello_constants.f90
-A  +    added_directory
-A  +    added_directory/hello_constants_dummy.inc
-A  +    added_directory/hello_constants.inc
-A  +    added_directory/hello_constants.f90
-M       lib/python/info/__init__.py
-M       lib/python/info/poems.py
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+status_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
  M      .
 A  +    added_directory
 A  +    added_file
+A  +    module/tree_conflict_file
 M       lib/python/info/__init__.py
 M       lib/python/info/poems.py
 M       module/hello_constants.f90
 M       module/hello_constants.inc
 M       module/hello_constants_dummy.inc
-A  +    module/tree_conflict_file
 M       subroutine/hello_sub_dummy.h
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests svn diff result of fcm merge branch-into-branch (1)
 TEST_KEY=$TEST_KEY_BASE-branch-into-branch-1-diff
 run_pass "$TEST_KEY" svn diff
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+diff_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
+
+Index: .
+===================================================================
+--- .	(revision 21)
++++ .	(working copy)
 
 Property changes on: .
 ___________________________________________________________________
 Added: svn:mergeinfo
    Merged /${PROJECT}trunk:r2-9
    Merged /${PROJECT}branches/dev/Share/merge1:r4-13
-
-Index: subroutine/hello_sub_dummy.h
-===================================================================
---- subroutine/hello_sub_dummy.h	(revision 20)
-+++ subroutine/hello_sub_dummy.h	(working copy)
-@@ -1 +1,2 @@
- #include "hello_sub.h"
-+Modified a line
-Index: module/hello_constants_dummy.inc
-===================================================================
---- module/hello_constants_dummy.inc	(revision 20)
-+++ module/hello_constants_dummy.inc	(working copy)
-@@ -1 +1 @@
--INCLUDE 'hello_constants.inc'
-+INCLUDE 'hello_constants.INc'
-Index: module/hello_constants.inc
-===================================================================
---- module/hello_constants.inc	(revision 20)
-+++ module/hello_constants.inc	(working copy)
-@@ -1 +1,2 @@
--CHARACTER (LEN=80), PARAMETER :: hello_string = 'Hello Earth!'
-+CHARACTER (
-+LEN=80), PARAMETER :: hello_strINg = 'Hello Earth!!'
-Index: module/hello_constants.f90
-===================================================================
---- module/hello_constants.f90	(revision 20)
-+++ module/hello_constants.f90	(working copy)
-@@ -1,6 +1,6 @@
- MODULE Hello_Constants
- 
--INCLUDE 'hello_constants_dummy.inc'
-+INCLUDE 'hello_constants_dummy.INc'
- 
- END MODULE Hello_Constants
- Second branch change
-Index: lib/python/info/__init__.py
-===================================================================
---- lib/python/info/__init__.py	(revision 20)
-+++ lib/python/info/__init__.py	(working copy)
-@@ -0,0 +1,2 @@
-+trunk change
-+another trunk change
-Index: lib/python/info/poems.py
-===================================================================
---- lib/python/info/poems.py	(revision 20)
-+++ lib/python/info/poems.py	(working copy)
-@@ -1,24 +1,23 @@
--#!/usr/bin/env python
--# -*- coding: utf-8 -*-
- """The Python, by Hilaire Belloc
- 
- A Python I should not advise,--
--It needs a doctor for its eyes,
-+It needs a doctor FOR its eyes,
- And has the measles yearly.
--However, if you feel inclined
--To get one (to improve your mind,
-+However, if you feel INclINed
-+To get one (
-+to improve your mINd,
- And not from fashion merely),
- Allow no music near its cage;
--And when it flies into a rage
-+And when it flies INto a rage
- Chastise it, most severely.
--I had an aunt in Yucatan
-+I had an aunt IN Yucatan
- Who bought a Python from a man
--And kept it for a pet.
-+And kept it FOR a pet.
- She died, because she never knew
- These simple little rules and few;--
--The Snake is living yet.
-+The Snake is livINg yet.
- """
- 
- import this
- 
--print "\n",  __doc__
-+prINt "\n",  __doc__
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
 Index: lib/python/info/__init__.py
 ===================================================================
---- lib/python/info/__init__.py	(revision 20)
+--- lib/python/info/__init__.py	(revision 21)
 +++ lib/python/info/__init__.py	(working copy)
 @@ -0,0 +1,2 @@
 +trunk change
 +another trunk change
 Index: lib/python/info/poems.py
 ===================================================================
---- lib/python/info/poems.py	(revision 20)
+--- lib/python/info/poems.py	(revision 21)
 +++ lib/python/info/poems.py	(working copy)
 @@ -1,24 +1,23 @@
 -#!/usr/bin/env python
@@ -1387,7 +1336,7 @@ Index: lib/python/info/poems.py
 +prINt "\n",  __doc__
 Index: module/hello_constants.f90
 ===================================================================
---- module/hello_constants.f90	(revision 20)
+--- module/hello_constants.f90	(revision 21)
 +++ module/hello_constants.f90	(working copy)
 @@ -1,6 +1,6 @@
  MODULE Hello_Constants
@@ -1399,7 +1348,7 @@ Index: module/hello_constants.f90
  Second branch change
 Index: module/hello_constants.inc
 ===================================================================
---- module/hello_constants.inc	(revision 20)
+--- module/hello_constants.inc	(revision 21)
 +++ module/hello_constants.inc	(working copy)
 @@ -1 +1,2 @@
 -CHARACTER (LEN=80), PARAMETER :: hello_string = 'Hello Earth!'
@@ -1407,30 +1356,19 @@ Index: module/hello_constants.inc
 +LEN=80), PARAMETER :: hello_strINg = 'Hello Earth!!'
 Index: module/hello_constants_dummy.inc
 ===================================================================
---- module/hello_constants_dummy.inc	(revision 20)
+--- module/hello_constants_dummy.inc	(revision 21)
 +++ module/hello_constants_dummy.inc	(working copy)
 @@ -1 +1 @@
 -INCLUDE 'hello_constants.inc'
 +INCLUDE 'hello_constants.INc'
 Index: subroutine/hello_sub_dummy.h
 ===================================================================
---- subroutine/hello_sub_dummy.h	(revision 20)
+--- subroutine/hello_sub_dummy.h	(revision 21)
 +++ subroutine/hello_sub_dummy.h	(working copy)
 @@ -1 +1,2 @@
  #include "hello_sub.h"
 +Modified a line
-Index: .
-===================================================================
---- .	(revision 20)
-+++ .	(working copy)
-
-Property changes on: .
-___________________________________________________________________
-Added: svn:mergeinfo
-   Merged /${PROJECT}trunk:r2-9
-   Merged /${PROJECT}branches/dev/Share/merge1:r4-13
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests fcm commit of fcm merge branch-into-branch (1)
@@ -1438,59 +1376,8 @@ TEST_KEY=$TEST_KEY_BASE-branch-into-branch-1-commit
 run_pass "$TEST_KEY" fcm commit <<__IN__
 y
 __IN__
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-[info] sed -i 1i\foo: starting commit message editor...
-Change summary:
---------------------------------------------------------------------------------
-[Root   : $REPOS_URL]
-[Project: ${TEST_PROJECT:-}]
-[Branch : branches/dev/Share/merge2]
-[Sub-dir: ]
-
- M      .
-M       subroutine/hello_sub_dummy.h
-A  +    added_file
-A  +    module/tree_conflict_file
-M       module/hello_constants_dummy.inc
-M       module/hello_constants.inc
-M       module/hello_constants.f90
-A  +    added_directory
-A  +    added_directory/hello_constants_dummy.inc
-A  +    added_directory/hello_constants.inc
-A  +    added_directory/hello_constants.f90
-M       lib/python/info/__init__.py
-M       lib/python/info/poems.py
---------------------------------------------------------------------------------
-Commit message is as follows:
---------------------------------------------------------------------------------
-foo
-Merged into /${PROJECT}branches/dev/Share/merge2: /${PROJECT}branches/dev/Share/merge1 at 13 cf. /${PROJECT}trunk at 1
---------------------------------------------------------------------------------
-
-*** WARNING: YOU ARE COMMITTING TO A Share BRANCH.
-*** Please ensure that you have the owner's permission.
-
-Would you like to commit this change?
-Enter "y" or "n" (or just press <return> for "n"): Sending        .
-Adding         added_directory
-Adding         added_directory/hello_constants.f90
-Adding         added_directory/hello_constants.inc
-Adding         added_directory/hello_constants_dummy.inc
-Adding         added_file
-Sending        lib/python/info/__init__.py
-Sending        lib/python/info/poems.py
-Sending        module/hello_constants.f90
-Sending        module/hello_constants.inc
-Sending        module/hello_constants_dummy.inc
-Adding         module/tree_conflict_file
-Sending        subroutine/hello_sub_dummy.h
-Transmitting file data ......
-Committed revision 21.
-At revision 21.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+commit_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
 [info] sed -i 1i\foo: starting commit message editor...
 Change summary:
 --------------------------------------------------------------------------------
@@ -1502,12 +1389,12 @@ Change summary:
  M      .
 A  +    added_directory
 A  +    added_file
+A  +    module/tree_conflict_file
 M       lib/python/info/__init__.py
 M       lib/python/info/poems.py
 M       module/hello_constants.f90
 M       module/hello_constants.inc
 M       module/hello_constants_dummy.inc
-A  +    module/tree_conflict_file
 M       subroutine/hello_sub_dummy.h
 --------------------------------------------------------------------------------
 Commit message is as follows:
@@ -1523,19 +1410,18 @@ Would you like to commit this change?
 Enter "y" or "n" (or just press <return> for "n"): Sending        .
 Adding         added_directory
 Adding         added_file
+Adding         module/tree_conflict_file
 Sending        lib/python/info/__init__.py
 Sending        lib/python/info/poems.py
 Sending        module/hello_constants.f90
 Sending        module/hello_constants.inc
 Sending        module/hello_constants_dummy.inc
-Adding         module/tree_conflict_file
 Sending        subroutine/hello_sub_dummy.h
 Transmitting file data ......
-Committed revision 21.
+Committed revision 22.
 Updating '.':
-At revision 21.
+At revision 22.
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests fcm log of fcm merge branch-into-branch (1)
@@ -1544,46 +1430,50 @@ run_pass "$TEST_KEY" fcm log $REPOS_URL
 sed -i "s/\(.*|.*|\).*\(|.*\)$/\1 date \2/g" $TEST_DIR/$TEST_KEY.out
 file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
 ------------------------------------------------------------------------
-r21 | $LOGNAME | date | 3 lines
+r22 | $LOGNAME | date | 3 lines
 
 foo
 Merged into /${PROJECT}branches/dev/Share/merge2: /${PROJECT}branches/dev/Share/merge1 at 13 cf. /${PROJECT}trunk at 1
 
 ------------------------------------------------------------------------
-r20 | $LOGNAME | date | 1 line
+r21 | $LOGNAME | date | 1 line
 
 Made branch change - added to ./module/hello_constants.f90
 ------------------------------------------------------------------------
-r19 | $LOGNAME | date | 3 lines
+r20 | $LOGNAME | date | 3 lines
 
 foo
-Merged into /${PROJECT}trunk: /${PROJECT}branches/dev/Share/merge1 at 18 cf. /${PROJECT}trunk at 15
+Merged into /${PROJECT}trunk: /${PROJECT}branches/dev/Share/merge1 at 19 cf. /${PROJECT}trunk at 16
 
 ------------------------------------------------------------------------
-r18 | $LOGNAME | date | 1 line
+r19 | $LOGNAME | date | 1 line
 
 Made branch change - deleted ./added_directory/hello_constants_dummy.inc, copied ./added_file
 ------------------------------------------------------------------------
-r17 | $LOGNAME | date | 3 lines
+r18 | $LOGNAME | date | 3 lines
 
 foo
-Merged into /${PROJECT}branches/dev/Share/merge1: /${PROJECT}trunk at 15 cf. /${PROJECT}branches/dev/Share/merge1 at 13
+Merged into /${PROJECT}branches/dev/Share/merge1: /${PROJECT}trunk at 16 cf. /${PROJECT}branches/dev/Share/merge1 at 13
 
 ------------------------------------------------------------------------
-r16 | $LOGNAME | date | 1 line
+r17 | $LOGNAME | date | 1 line
 
 Made branch change for merge repeat test
 ------------------------------------------------------------------------
-r15 | $LOGNAME | date | 1 line
+r16 | $LOGNAME | date | 1 line
 
 Made trunk change - a simple edit of ./added_file
 ------------------------------------------------------------------------
-r14 | $LOGNAME | date | 3 lines
+r15 | $LOGNAME | date | 3 lines
 
 foo
 Merged into /${PROJECT}trunk: /${PROJECT}branches/dev/Share/merge1 at 13 cf. /${PROJECT}branches/dev/Share/merge1 at 11
 
 ------------------------------------------------------------------------
+r14 | $LOGNAME | date | 1 line
+
+Made a branch Created /branches/dev/Share/merge3 from /trunk at 1.
+------------------------------------------------------------------------
 r13 | $LOGNAME | date | 1 line
 
 Made branch change to add extra feature
@@ -1642,5 +1532,43 @@ initial trunk import
 ------------------------------------------------------------------------
 __OUT__
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
+#------------------------------------------------------------------------------
+# Test the various mergeinfo output after merging.
+test_mergeinfo "$TEST_KEY_BASE-branch-into-branch-1-post" \
+    $ROOT_URL/branches/dev/Share/merge1 <<__RESULTS__
+begin-prop
+/branches/dev/Share/merge1:4-13
+/trunk:2-9
+end-prop
+begin-info
+    youngest common ancestor
+    |         last full merge
+    |         |        tip of branch
+    |         |        |         repository path
+
+    1         13       22      
+    |         |        |       
+       --| |------------         branches/dev/Share/merge1
+  ... /        \               
+      \         \              
+       --| |------------         branches/dev/Share/merge2
+                       |       
+                       22      
+end-info
+begin-eligible
+r17
+r18
+r19
+end-eligible
+begin-merged
+r4
+r5
+r10
+r11
+r13
+end-merged
+__RESULTS__
+
+#-------------------------------------------------------------------------------
 teardown
 #-------------------------------------------------------------------------------
diff --git a/t/fcm-merge/02-reverse.t b/t/fcm-merge/02-reverse.t
new file mode 100755
index 0000000..658d9a2
--- /dev/null
+++ b/t/fcm-merge/02-reverse.t
@@ -0,0 +1,135 @@
+#!/bin/bash
+# ------------------------------------------------------------------------------
+# (C) British Crown Copyright 2006-15 Met Office.
+#
+# This file is part of FCM, tools for managing and building source code.
+#
+# FCM is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# FCM is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with FCM. If not, see <http://www.gnu.org/licenses/>.
+# ------------------------------------------------------------------------------
+# Basic tests for "fcm merge --reverse".
+#-------------------------------------------------------------------------------
+. "$(dirname "$0")/test_header"
+#-------------------------------------------------------------------------------
+check_svn_version
+tests 13
+#-------------------------------------------------------------------------------
+svnadmin create 'foo'
+URL_FOO="file://${PWD}/foo"
+svn mkdir -q -m"season greetings" --no-auth-cache "${URL_FOO}/greet"
+echo 'Merry Xmas' >'xmas.txt'
+echo 'Happy New Year' >'new-year.txt'
+for NAME in 'xmas.txt' 'new-year.txt'; do
+    svn import -q -m"import ${NAME}" --no-auth-cache \
+        "${NAME}" "${URL_FOO}/greet/${NAME}"
+done
+svn mkdir -q -m"hello world" --no-auth-cache --parents "${URL_FOO}/hello/trunk"
+svn co -q "${URL_FOO}/hello/trunk" 'hello-wc'
+cat >'hello-wc/world.txt' <<'__TXT__'
+Hello Mercury!
+Hello Venus!
+Hollow Earth!
+Hello Mars!
+__TXT__
+svn add -q 'hello-wc/world.txt'
+svn ci -q -m'hollow worlds' --no-auth-cache 'hello-wc'
+cat >'hello-wc/world.txt' <<'__TXT__'
+Hello Mercury!
+Hello Venus!
+Hello Earth!
+Hello Mars!
+__TXT__
+svn ci -q -m'hello worlds' --no-auth-cache 'hello-wc'
+rm -fr 'hello-wc'
+#-------------------------------------------------------------------------------
+TEST_KEY="${TEST_KEY_BASE}-r3"
+svn co -q "${URL_FOO}/greet" 'greet-wc'
+cd 'greet-wc'
+run_pass "${TEST_KEY}" fcm merge --reverse --non-interactive
+cd ..
+svn status 'greet-wc' >"${TEST_KEY}.status"
+file_cmp "${TEST_KEY}.status" "${TEST_KEY}.status" <<'__STATUS__'
+D       greet-wc/new-year.txt
+__STATUS__
+file_cmp "${TEST_KEY}.message" 'greet-wc/#commit_message#' <<'__MESSAGE__'
+--FCM message (will be inserted automatically)--
+Reversed r3 of /greet
+
+__MESSAGE__
+rm -rf 'greet-wc'
+#-------------------------------------------------------------------------------
+TEST_KEY="${TEST_KEY_BASE}-r2"
+svn co -q "${URL_FOO}/greet" 'greet-wc'
+cd 'greet-wc'
+run_pass "${TEST_KEY}" fcm merge --reverse -r 2 --non-interactive
+cd ..
+
+svn status 'greet-wc' >"${TEST_KEY}.status"
+file_cmp "${TEST_KEY}.status" "${TEST_KEY}.status" <<'__STATUS__'
+D       greet-wc/xmas.txt
+__STATUS__
+file_cmp "${TEST_KEY}.message" 'greet-wc/#commit_message#' <<'__MESSAGE__'
+--FCM message (will be inserted automatically)--
+Reversed r2 of /greet
+
+__MESSAGE__
+rm -rf 'greet-wc'
+#-------------------------------------------------------------------------------
+TEST_KEY="${TEST_KEY_BASE}-r2-r3"
+svn co -q "${URL_FOO}/greet" 'greet-wc'
+cd 'greet-wc'
+run_pass "${TEST_KEY}" fcm merge --reverse -r 3:1 --non-interactive
+cd ..
+
+svn status 'greet-wc' | sort >"${TEST_KEY}.status"
+file_cmp "${TEST_KEY}.status" "${TEST_KEY}.status" <<'__STATUS__'
+D       greet-wc/new-year.txt
+D       greet-wc/xmas.txt
+__STATUS__
+file_cmp "${TEST_KEY}.message" 'greet-wc/#commit_message#' <<'__MESSAGE__'
+--FCM message (will be inserted automatically)--
+Reversed r3:1 of /greet
+
+__MESSAGE__
+rm -rf 'greet-wc'
+#-------------------------------------------------------------------------------
+TEST_KEY="${TEST_KEY_BASE}-r6"
+svn co -q "${URL_FOO}/hello/trunk" 'hello-wc'
+cd 'hello-wc'
+run_pass "${TEST_KEY}" fcm merge --reverse --non-interactive
+cd ..
+svn status 'hello-wc' >"${TEST_KEY}.status"
+file_cmp "${TEST_KEY}.status" "${TEST_KEY}.status" <<'__STATUS__'
+M       hello-wc/world.txt
+__STATUS__
+svn diff 'hello-wc' >"${TEST_KEY}.diff"
+file_cmp "${TEST_KEY}.diff" "${TEST_KEY}.diff" <<'__DIFF__'
+Index: hello-wc/world.txt
+===================================================================
+--- hello-wc/world.txt	(revision 6)
++++ hello-wc/world.txt	(working copy)
+@@ -1,4 +1,4 @@
+ Hello Mercury!
+ Hello Venus!
+-Hello Earth!
++Hollow Earth!
+ Hello Mars!
+__DIFF__
+file_cmp "${TEST_KEY}.message" 'hello-wc/#commit_message#' <<'__MESSAGE__'
+--FCM message (will be inserted automatically)--
+Reversed r6 of /hello/trunk
+
+__MESSAGE__
+rm -rf 'hello-wc'
+#-------------------------------------------------------------------------------
+exit
diff --git a/t/fcm-merge/test_header b/t/fcm-merge/test_header
index 672ce12..206061d 100644
--- a/t/fcm-merge/test_header
+++ b/t/fcm-merge/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -210,6 +210,44 @@ function run_fail() {
     pass $TEST_KEY
 }
 
+function get_results() {
+    local RESULT_KEY=$1
+    local RESULTS_FILE=$2
+    local BEGIN="^begin-$RESULT_KEY$"
+    local END="^end-$RESULT_KEY$"
+    local RESULTS_TEMP=$(mktemp)
+    sed -n "/$BEGIN/,/$END/{/$BEGIN\|$END/d; p;}" $RESULTS_FILE >$RESULTS_TEMP
+    echo $RESULTS_TEMP
+}
+
+function test_mergeinfo() {
+    local TEST_INFO_NAME="$1-svn-mergeinfo"
+    local DIFF_BRANCH=$2
+    local INPUT_RESULTS_FILE=${3:--}
+    local RESULTS_FILE=$(mktemp)
+    cat "$INPUT_RESULTS_FILE" > "$RESULTS_FILE"
+    # Test svn:mergeinfo property.
+    TEST_KEY=$TEST_INFO_NAME-prop
+    run_pass "$TEST_KEY" svn propget svn:mergeinfo .
+    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <$(get_results prop $RESULTS_FILE)
+    file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
+    # Test svn mergeinfo output.
+    TEST_KEY=$TEST_INFO_NAME-info
+    run_pass "$TEST_KEY" svn mergeinfo $DIFF_BRANCH
+    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <$(get_results info $RESULTS_FILE)    
+    file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
+    # Test svn mergeinfo show-revs eligible before merge.
+    TEST_KEY=$TEST_INFO_NAME-show-revs-eligible
+    run_pass "$TEST_KEY" svn mergeinfo --show-revs eligible $DIFF_BRANCH
+    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <$(get_results eligible $RESULTS_FILE)        
+    file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
+    # Test svn mergeinfo show-revs merged before merge.
+    TEST_KEY=$TEST_INFO_NAME-show-revs-merged
+    run_pass "$TEST_KEY" svn mergeinfo --show-revs merged $DIFF_BRANCH
+    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <$(get_results merged $RESULTS_FILE)            
+    file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
+}
+
 function setup() {
     mkdir -p $TEST_DIR/.subversion
     mkdir -p $TEST_DIR/run
diff --git a/t/fcm-recover-svn-repos/00-basic.t b/t/fcm-recover-svn-repos/00-basic.t
index d334ec2..6abd48f 100755
--- a/t/fcm-recover-svn-repos/00-basic.t
+++ b/t/fcm-recover-svn-repos/00-basic.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-status/00-simple.t b/t/fcm-status/00-simple.t
index 9d2bad3..f248dcf 100644
--- a/t/fcm-status/00-simple.t
+++ b/t/fcm-status/00-simple.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 4
 #-------------------------------------------------------------------------------
 setup
@@ -43,26 +44,8 @@ svn delete -q --force lib/python/info/poems.py
 # Tests fcm status result of fcm merge (1)
 TEST_KEY=$TEST_KEY_BASE-status
 run_pass "$TEST_KEY" fcm status --config-dir=$TEST_DIR/.subversion
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
- M      .
-?       unversioned_file
-!       subroutine/hello_sub.h
-M       subroutine/hello_sub_dummy.h
-      C added_file
-      >   local add, incoming add upon merge
-A  +    module/tree_conflict_file
-M       module/hello_constants_dummy.inc
-M       module/hello_constants.inc
-M       module/hello_constants.f90
-A  +    added_directory
-A  +    added_directory/hello_constants_dummy.inc
-A  +    added_directory/hello_constants.inc
-A  +    added_directory/hello_constants.f90
-D       lib/python/info/poems.py
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+status_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
  M      .
 A  +    added_directory
       C added_file
@@ -78,6 +61,5 @@ M       subroutine/hello_sub_dummy.h
 Summary of conflicts:
   Tree conflicts: 1
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
diff --git a/t/fcm-status/test_header b/t/fcm-status/test_header
index 672ce12..6d52eac 100644
--- a/t/fcm-status/test_header
+++ b/t/fcm-status/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-switch/00-simple.t b/t/fcm-switch/00-simple.t
index 62583aa..7d9112a 100644
--- a/t/fcm-switch/00-simple.t
+++ b/t/fcm-switch/00-simple.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 12
 #-------------------------------------------------------------------------------
 setup
@@ -32,20 +33,21 @@ cd $TEST_DIR/wc
 # Tests fcm switch trunk
 svn switch -q $ROOT_URL/branches/dev/Share/merge1
 TEST_KEY=$TEST_KEY_BASE-trunk
-run_pass "$TEST_KEY" fcm switch trunk <<<'y'
-file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+run_pass "$TEST_KEY" fcm switch trunk <<<"y"
+merge_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
 switch: status of "$TEST_DIR/wc":
 ?       unversioned_file
 switch: continue?
 Enter "y" or "n" (or just press <return> for "n"): D    added_file
 D    added_directory
-U    subroutine/hello_sub_dummy.h
 D    module/tree_conflict_file
-U    module/hello_constants_dummy.inc
-U    module/hello_constants.inc
-U    module/hello_constants.f90
 U    lib/python/info/__init__.py
 U    lib/python/info/poems.py
+U    module/hello_constants.f90
+U    module/hello_constants.inc
+U    module/hello_constants_dummy.inc
+U    subroutine/hello_sub_dummy.h
 Updated to revision 9.
 __OUT__
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
@@ -54,19 +56,20 @@ file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 rm unversioned_file
 TEST_KEY=$TEST_KEY_BASE-branch-1
 run_pass "$TEST_KEY" fcm switch branches/dev/Share/merge1 <<<'y'
-file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-U    subroutine/hello_sub_dummy.h
-A    added_file
+merge_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
 A    added_directory
-A    added_directory/hello_constants_dummy.inc
-A    added_directory/hello_constants.inc
 A    added_directory/hello_constants.f90
+A    added_directory/hello_constants.inc
+A    added_directory/hello_constants_dummy.inc
+A    added_file
 A    module/tree_conflict_file
-U    module/hello_constants_dummy.inc
-U    module/hello_constants.inc
-U    module/hello_constants.f90
 U    lib/python/info/__init__.py
 U    lib/python/info/poems.py
+U    module/hello_constants.f90
+U    module/hello_constants.inc
+U    module/hello_constants_dummy.inc
+U    subroutine/hello_sub_dummy.h
 Updated to revision 9.
 __OUT__
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
@@ -74,36 +77,34 @@ file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 # Tests fcm switch merge2 branch
 TEST_KEY=$TEST_KEY_BASE-branch-2
 run_pass "$TEST_KEY" fcm switch --non-interactive dev/Share/merge2
-file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-D    added_file
-D    added_directory
+merge_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
  U   subroutine/hello_sub.h
-U    subroutine/hello_sub_dummy.h
+A    renamed_added_file
+D    added_directory
+D    added_file
 D    module/tree_conflict_file
-U    module/hello_constants_dummy.inc
-U    module/hello_constants.inc
-U    module/hello_constants.f90
 U    lib/python/info/poems.py
-A    renamed_added_file
+U    module/hello_constants.f90
+U    module/hello_constants.inc
+U    module/hello_constants_dummy.inc
+U    subroutine/hello_sub_dummy.h
 Updated to revision 9.
 __OUT__
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests fcm switch trunk, without .svn/entries
 TEST_KEY=$TEST_KEY_BASE-trunk-2
-if $SVN_VERSION_IS_16; then
-    skip 3 "$TEST_KEY won't work under Subversion 1.6"
-else
-    rm -f .svn/entries
-    run_pass "$TEST_KEY" fcm switch trunk <<<'y'
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<'__OUT__'
-D    renamed_added_file
+rm -f .svn/entries
+run_pass "$TEST_KEY" fcm switch trunk <<<'y'
+merge_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<'__OUT__'
  U   subroutine/hello_sub.h
+D    renamed_added_file
 U    lib/python/info/__init__.py
 Updated to revision 9.
 __OUT__
-    file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
-fi
+file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 teardown
 exit
diff --git a/t/fcm-switch/01-subtree.t b/t/fcm-switch/01-subtree.t
index cccb0b7..1569c5f 100644
--- a/t/fcm-switch/01-subtree.t
+++ b/t/fcm-switch/01-subtree.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,6 +21,7 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
+check_svn_version
 tests 9
 #-------------------------------------------------------------------------------
 setup
@@ -36,39 +37,22 @@ cd module
 run_pass "$TEST_KEY" fcm switch trunk <<__IN__
 y
 __IN__
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+merge_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
 switch: status of "$TEST_DIR/wc":
 ?       $TEST_DIR/wc/unversioned_file
 switch: continue?
 Enter "y" or "n" (or just press <return> for "n"): D    $TEST_DIR/wc/added_file
 D    $TEST_DIR/wc/added_directory
-U    $TEST_DIR/wc/subroutine/hello_sub_dummy.h
-D    $TEST_DIR/wc/module/tree_conflict_file
-U    $TEST_DIR/wc/module/hello_constants_dummy.inc
-U    $TEST_DIR/wc/module/hello_constants.inc
-U    $TEST_DIR/wc/module/hello_constants.f90
+D    tree_conflict_file
 U    $TEST_DIR/wc/lib/python/info/__init__.py
 U    $TEST_DIR/wc/lib/python/info/poems.py
-Updated to revision 9.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-switch: status of "$TEST_DIR/wc":
-?       $TEST_DIR/wc/unversioned_file
-switch: continue?
-Enter "y" or "n" (or just press <return> for "n"): D    $TEST_DIR/wc/added_file
-D    $TEST_DIR/wc/added_directory
 U    $TEST_DIR/wc/subroutine/hello_sub_dummy.h
-D    tree_conflict_file
-U    hello_constants_dummy.inc
-U    hello_constants.inc
 U    hello_constants.f90
-U    $TEST_DIR/wc/lib/python/info/__init__.py
-U    $TEST_DIR/wc/lib/python/info/poems.py
+U    hello_constants.inc
+U    hello_constants_dummy.inc
 Updated to revision 9.
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests fcm switch merge1 branch
@@ -77,73 +61,41 @@ TEST_KEY=$TEST_KEY_BASE-branch-1
 run_pass "$TEST_KEY" fcm switch branches/dev/Share/merge1 <<__IN__
 y
 __IN__
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-U    $TEST_DIR/wc/subroutine/hello_sub_dummy.h
-A    $TEST_DIR/wc/added_file
+merge_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
 A    $TEST_DIR/wc/added_directory
-A    $TEST_DIR/wc/added_directory/hello_constants_dummy.inc
-A    $TEST_DIR/wc/added_directory/hello_constants.inc
 A    $TEST_DIR/wc/added_directory/hello_constants.f90
-A    $TEST_DIR/wc/module/tree_conflict_file
-U    $TEST_DIR/wc/module/hello_constants_dummy.inc
-U    $TEST_DIR/wc/module/hello_constants.inc
-U    $TEST_DIR/wc/module/hello_constants.f90
-U    $TEST_DIR/wc/lib/python/info/__init__.py
-U    $TEST_DIR/wc/lib/python/info/poems.py
-Updated to revision 9.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-U    $TEST_DIR/wc/subroutine/hello_sub_dummy.h
-A    $TEST_DIR/wc/added_file
-A    $TEST_DIR/wc/added_directory
-A    $TEST_DIR/wc/added_directory/hello_constants_dummy.inc
 A    $TEST_DIR/wc/added_directory/hello_constants.inc
-A    $TEST_DIR/wc/added_directory/hello_constants.f90
+A    $TEST_DIR/wc/added_directory/hello_constants_dummy.inc
+A    $TEST_DIR/wc/added_file
 A    tree_conflict_file
-U    hello_constants_dummy.inc
-U    hello_constants.inc
-U    hello_constants.f90
 U    $TEST_DIR/wc/lib/python/info/__init__.py
 U    $TEST_DIR/wc/lib/python/info/poems.py
+U    $TEST_DIR/wc/subroutine/hello_sub_dummy.h
+U    hello_constants.f90
+U    hello_constants.inc
+U    hello_constants_dummy.inc
 Updated to revision 9.
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests fcm switch merge2 branch
 TEST_KEY=$TEST_KEY_BASE-branch-2
 run_pass "$TEST_KEY" fcm switch --non-interactive dev/Share/merge2
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-D    $TEST_DIR/wc/added_file
-D    $TEST_DIR/wc/added_directory
+merge_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
  U   $TEST_DIR/wc/subroutine/hello_sub.h
-U    $TEST_DIR/wc/subroutine/hello_sub_dummy.h
-D    $TEST_DIR/wc/module/tree_conflict_file
-U    $TEST_DIR/wc/module/hello_constants_dummy.inc
-U    $TEST_DIR/wc/module/hello_constants.inc
-U    $TEST_DIR/wc/module/hello_constants.f90
-U    $TEST_DIR/wc/lib/python/info/poems.py
 A    $TEST_DIR/wc/renamed_added_file
-Updated to revision 9.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-D    $TEST_DIR/wc/added_file
 D    $TEST_DIR/wc/added_directory
- U   $TEST_DIR/wc/subroutine/hello_sub.h
-U    $TEST_DIR/wc/subroutine/hello_sub_dummy.h
+D    $TEST_DIR/wc/added_file
 D    tree_conflict_file
-U    hello_constants_dummy.inc
-U    hello_constants.inc
-U    hello_constants.f90
 U    $TEST_DIR/wc/lib/python/info/poems.py
-A    $TEST_DIR/wc/renamed_added_file
+U    $TEST_DIR/wc/subroutine/hello_sub_dummy.h
+U    hello_constants.f90
+U    hello_constants.inc
+U    hello_constants_dummy.inc
 Updated to revision 9.
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 teardown
 #-------------------------------------------------------------------------------
diff --git a/t/fcm-switch/test_header b/t/fcm-switch/test_header
index 672ce12..6d52eac 100644
--- a/t/fcm-switch/test_header
+++ b/t/fcm-switch/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/fcm-update/00-simple.t b/t/fcm-update/00-simple.t
index 1948c9d..0b1c7a2 100644
--- a/t/fcm-update/00-simple.t
+++ b/t/fcm-update/00-simple.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,7 +21,8 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
-tests 6
+check_svn_version
+tests 7
 #-------------------------------------------------------------------------------
 setup
 init_repos
@@ -35,38 +36,22 @@ TEST_KEY=$TEST_KEY_BASE-r-PREV
 run_pass "$TEST_KEY" fcm update -r PREV <<__IN__
 y
 __IN__
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-update: status of ".":
-?       unversioned_file
-update: continue?
-Enter "y" or "n" (or just press <return> for "n"): D    added_file
-D    added_directory
-U    subroutine/hello_sub_dummy.h
-D    module/tree_conflict_file
-U    module/hello_constants_dummy.inc
-U    module/hello_constants.inc
-U    module/hello_constants.f90
-U    lib/python/info/poems.py
-Updated to revision 4.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+merge_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
 update: status of ".":
 ?       unversioned_file
 update: continue?
 Enter "y" or "n" (or just press <return> for "n"): Updating '.':
-D    added_file
 D    added_directory
-U    subroutine/hello_sub_dummy.h
+D    added_file
 D    module/tree_conflict_file
-U    module/hello_constants_dummy.inc
-U    module/hello_constants.inc
-U    module/hello_constants.f90
 U    lib/python/info/poems.py
+U    module/hello_constants.f90
+U    module/hello_constants.inc
+U    module/hello_constants_dummy.inc
+U    subroutine/hello_sub_dummy.h
 Updated to revision 4.
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests fcm update
@@ -75,40 +60,10 @@ TEST_KEY=$TEST_KEY_BASE-normal
 run_pass "$TEST_KEY" fcm update <<__IN__
 y
 __IN__
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-update: status of ".":
-        *        4   subroutine/hello_sub_dummy.h
-        *            added_directory/hello_constants.f90
-        *            added_directory/hello_constants_dummy.inc
-        *            added_directory/hello_constants.inc
-        *            added_directory
-        *        4   module/hello_constants.f90
-        *            module/tree_conflict_file
-        *        4   module/hello_constants_dummy.inc
-        *        4   module/hello_constants.inc
-        *        4   module
-        *        4   lib/python/info/poems.py
-        *            added_file
-        *        4   .
-update: continue?
-Enter "y" or "n" (or just press <return> for "n"): U    subroutine/hello_sub_dummy.h
-A    added_file
-A    added_directory
-A    added_directory/hello_constants_dummy.inc
-A    added_directory/hello_constants.inc
-A    added_directory/hello_constants.f90
-A    module/tree_conflict_file
-U    module/hello_constants_dummy.inc
-U    module/hello_constants.inc
-U    module/hello_constants.f90
-U    lib/python/info/poems.py
-Updated to revision 9.
-__OUT__
-else
-    # The output is now not deterministic for svn update!!
-    sort $TEST_DIR/"$TEST_KEY.out" -o $TEST_DIR/"$TEST_KEY.out"
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+sed -n "/^  *\*/p" "$TEST_DIR/$TEST_KEY.out" | LANG=C sort -o \
+    "$TEST_DIR/$TEST_KEY.update-status.sorted.out"
+file_cmp "$TEST_KEY.update-status.sorted.out" \
+         "$TEST_KEY.update-status.sorted.out" <<__OUT__
         *            added_directory
         *            added_directory/hello_constants.f90
         *            added_directory/hello_constants.inc
@@ -122,23 +77,26 @@ else
         *        4   module/hello_constants.inc
         *        4   module/hello_constants_dummy.inc
         *        4   subroutine/hello_sub_dummy.h
+__OUT__
+sed -i "/^  *\*/d" "$TEST_DIR/$TEST_KEY.out"
+merge_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
+update: status of ".":
+update: continue?
+Enter "y" or "n" (or just press <return> for "n"): Updating '.':
 A    added_directory
 A    added_directory/hello_constants.f90
 A    added_directory/hello_constants.inc
 A    added_directory/hello_constants_dummy.inc
 A    added_file
 A    module/tree_conflict_file
-Enter "y" or "n" (or just press <return> for "n"): Updating '.':
 U    lib/python/info/poems.py
 U    module/hello_constants.f90
 U    module/hello_constants.inc
 U    module/hello_constants_dummy.inc
 U    subroutine/hello_sub_dummy.h
 Updated to revision 9.
-update: continue?
-update: status of ".":
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 teardown
 #-------------------------------------------------------------------------------
diff --git a/t/fcm-update/01-subtree.t b/t/fcm-update/01-subtree.t
index 061eba4..42b8d44 100644
--- a/t/fcm-update/01-subtree.t
+++ b/t/fcm-update/01-subtree.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -21,7 +21,8 @@
 #-------------------------------------------------------------------------------
 . $(dirname $0)/test_header
 #-------------------------------------------------------------------------------
-tests 6
+check_svn_version
+tests 7
 #-------------------------------------------------------------------------------
 setup
 init_repos
@@ -36,38 +37,22 @@ cd module
 run_pass "$TEST_KEY" fcm update -r PREV <<__IN__
 y
 __IN__
-if $SVN_VERSION_IS_16; then
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-update: status of "$TEST_DIR/wc":
-?       $TEST_DIR/wc/unversioned_file
-update: continue?
-Enter "y" or "n" (or just press <return> for "n"): D    $TEST_DIR/wc/added_file
-D    $TEST_DIR/wc/added_directory
-U    $TEST_DIR/wc/subroutine/hello_sub_dummy.h
-D    $TEST_DIR/wc/module/tree_conflict_file
-U    $TEST_DIR/wc/module/hello_constants_dummy.inc
-U    $TEST_DIR/wc/module/hello_constants.inc
-U    $TEST_DIR/wc/module/hello_constants.f90
-U    $TEST_DIR/wc/lib/python/info/poems.py
-Updated to revision 4.
-__OUT__
-else
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+merge_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
 update: status of "$TEST_DIR/wc":
 ?       $TEST_DIR/wc/unversioned_file
 update: continue?
 Enter "y" or "n" (or just press <return> for "n"): Updating '$TEST_DIR/wc':
-D    $TEST_DIR/wc/added_file
 D    $TEST_DIR/wc/added_directory
-U    $TEST_DIR/wc/subroutine/hello_sub_dummy.h
+D    $TEST_DIR/wc/added_file
 D    tree_conflict_file
-U    hello_constants_dummy.inc
-U    hello_constants.inc
-U    hello_constants.f90
 U    $TEST_DIR/wc/lib/python/info/poems.py
+U    $TEST_DIR/wc/subroutine/hello_sub_dummy.h
+U    hello_constants.f90
+U    hello_constants.inc
+U    hello_constants_dummy.inc
 Updated to revision 4.
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 #-------------------------------------------------------------------------------
 # Tests fcm update
@@ -76,9 +61,10 @@ TEST_KEY=$TEST_KEY_BASE-normal
 run_pass "$TEST_KEY" fcm update <<__IN__
 y
 __IN__
-if $SVN_VERSION_IS_16; then
-    sort $TEST_DIR/"$TEST_KEY.out" -o $TEST_DIR/"$TEST_KEY.out"
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
+sed -n "/^  *\*/p" "$TEST_DIR/$TEST_KEY.out" | LANG=C sort -o \
+    "$TEST_DIR/$TEST_KEY.update-status.sorted.out"
+file_cmp "$TEST_KEY.update-status.sorted.out" \
+         "$TEST_KEY.update-status.sorted.out" <<__OUT__
         *            $TEST_DIR/wc/added_directory
         *            $TEST_DIR/wc/added_directory/hello_constants.f90
         *            $TEST_DIR/wc/added_directory/hello_constants.inc
@@ -92,55 +78,26 @@ if $SVN_VERSION_IS_16; then
         *        4   $TEST_DIR/wc/module/hello_constants.inc
         *        4   $TEST_DIR/wc/module/hello_constants_dummy.inc
         *        4   $TEST_DIR/wc/subroutine/hello_sub_dummy.h
-A    $TEST_DIR/wc/added_directory
-A    $TEST_DIR/wc/added_directory/hello_constants.f90
-A    $TEST_DIR/wc/added_directory/hello_constants.inc
-A    $TEST_DIR/wc/added_directory/hello_constants_dummy.inc
-A    $TEST_DIR/wc/added_file
-A    $TEST_DIR/wc/module/tree_conflict_file
-Enter "y" or "n" (or just press <return> for "n"): U    $TEST_DIR/wc/subroutine/hello_sub_dummy.h
-U    $TEST_DIR/wc/lib/python/info/poems.py
-U    $TEST_DIR/wc/module/hello_constants.f90
-U    $TEST_DIR/wc/module/hello_constants.inc
-U    $TEST_DIR/wc/module/hello_constants_dummy.inc
-Updated to revision 9.
-update: continue?
-update: status of "$TEST_DIR/wc":
 __OUT__
-else
-    # The output is now not deterministic for svn update!!
-    sort $TEST_DIR/"$TEST_KEY.out" -o $TEST_DIR/"$TEST_KEY.out"
-    file_cmp "$TEST_KEY.out" "$TEST_KEY.out" <<__OUT__
-        *            $TEST_DIR/wc/added_directory
-        *            $TEST_DIR/wc/added_directory/hello_constants.f90
-        *            $TEST_DIR/wc/added_directory/hello_constants.inc
-        *            $TEST_DIR/wc/added_directory/hello_constants_dummy.inc
-        *            $TEST_DIR/wc/added_file
-        *            $TEST_DIR/wc/module/tree_conflict_file
-        *        4   $TEST_DIR/wc
-        *        4   $TEST_DIR/wc/lib/python/info/poems.py
-        *        4   $TEST_DIR/wc/module
-        *        4   $TEST_DIR/wc/module/hello_constants.f90
-        *        4   $TEST_DIR/wc/module/hello_constants.inc
-        *        4   $TEST_DIR/wc/module/hello_constants_dummy.inc
-        *        4   $TEST_DIR/wc/subroutine/hello_sub_dummy.h
+sed -i "/^  *\*/d" "$TEST_DIR/$TEST_KEY.out"
+merge_sort "$TEST_DIR/$TEST_KEY.out" "$TEST_DIR/$TEST_KEY.sorted.out"
+file_cmp "$TEST_KEY.sorted.out" "$TEST_KEY.sorted.out" <<__OUT__
+update: status of "$TEST_DIR/wc":
+update: continue?
+Enter "y" or "n" (or just press <return> for "n"): Updating '$TEST_DIR/wc':
 A    $TEST_DIR/wc/added_directory
 A    $TEST_DIR/wc/added_directory/hello_constants.f90
 A    $TEST_DIR/wc/added_directory/hello_constants.inc
 A    $TEST_DIR/wc/added_directory/hello_constants_dummy.inc
 A    $TEST_DIR/wc/added_file
 A    tree_conflict_file
-Enter "y" or "n" (or just press <return> for "n"): Updating '$TEST_DIR/wc':
 U    $TEST_DIR/wc/lib/python/info/poems.py
 U    $TEST_DIR/wc/subroutine/hello_sub_dummy.h
 U    hello_constants.f90
 U    hello_constants.inc
 U    hello_constants_dummy.inc
 Updated to revision 9.
-update: continue?
-update: status of "$TEST_DIR/wc":
 __OUT__
-fi
 file_cmp "$TEST_KEY.err" "$TEST_KEY.err" </dev/null
 teardown
 #-------------------------------------------------------------------------------
diff --git a/t/fcm-update/test_header b/t/fcm-update/test_header
index 672ce12..6d52eac 100644
--- a/t/fcm-update/test_header
+++ b/t/fcm-update/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/lib/bash/test_header b/t/lib/bash/test_header
index 1d5e010..30213c4 100644
--- a/t/lib/bash/test_header
+++ b/t/lib/bash/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -56,6 +56,16 @@
 #         -e if not specified.
 #     file_grep TEST_KEY PATTERN FILE
 #         Run "grep -q PATTERN FILE". pass/fail $TEST_KEY accordingly.
+#     commit_sort INPUT_FILE OUTPUT_FILE
+#         Sort status and transmitting info within the commit output.
+#     diff_sort INPUT_FILE OUTPUT_FILE
+#         Sort Subversion diff output by filename.
+#     status_sort INPUT_FILE OUTPUT_FILE
+#         Sort Subversion status lines.
+#     merge_sort INPUT_FILE OUTPUT_FILE
+#         Sort Subversion merge status lines.
+#     check_svn_version
+#         Check Subversion version and skip tests if not compatible.
 #     FINALLY
 #         This is run on EXIT or INT to remove the temporary working directory
 #         for the test. Call FINALLY_MORE if it is declared.
@@ -65,8 +75,6 @@
 #         Root of FCM's installation. (Exported.)
 #     SIGNALS
 #         List of signals trapped by FINALLY, currently EXIT and INT.
-#     SVN_VERSION_IS_16
-#         True if "svn --version" returns 1.6*.
 #     TEST_DIR
 #         Temporary directory that is also the working directory for this test.
 #     TEST_KEY_BASE
@@ -178,6 +186,72 @@ function file_grep() {
     fail $TEST_KEY
 }
 
+function commit_sort() {
+    local INPUT_FILE=$1
+    local OUTPUT_FILE=$2
+    local TMP_OUTPUT_FILE=$(mktemp)
+    status_sort $INPUT_FILE $TMP_OUTPUT_FILE
+    python -c 'import re, sys
+text = sys.stdin.read()
+sending_lines = re.findall("^\w+ing  +.*$", text, re.M)
+prefix = text[:text.index(sending_lines[0])]
+suffix = text[(text.index(sending_lines[-1]) + len(sending_lines[-1])):]
+sending_lines.sort()
+print prefix + "\n".join(sending_lines) + suffix.rstrip()
+' <"$TMP_OUTPUT_FILE" >"$OUTPUT_FILE"
+    rm "$TMP_OUTPUT_FILE"
+}
+
+function diff_sort() {
+    local INPUT_FILE=$1
+    local OUTPUT_FILE=$2
+    python -c 'import re, sys
+text = sys.stdin.read()
+print "\nIndex: ".join(
+    [l.strip() for l in sorted(re.compile("^Index: ", re.M).split(text))])
+' <"$INPUT_FILE" >"$OUTPUT_FILE"
+}
+
+function status_sort() {
+    local INPUT_FILE=$1
+    local OUTPUT_FILE=$2
+    python -c 'import re, sys
+text = sys.stdin.read()
+status_lines = re.findall("^.{7} [\w./].*$", text, re.M)
+prefix = text[:text.index(status_lines[0])]
+suffix = text[(text.index(status_lines[-1]) + len(status_lines[-1])):]
+status_lines.sort()
+print prefix + "\n".join(status_lines) + suffix.rstrip()
+' <"$INPUT_FILE" >"$OUTPUT_FILE"
+}
+
+function merge_sort() {
+    local INPUT_FILE=$1
+    local OUTPUT_FILE=$2
+    python -c 'import re, sys
+text = sys.stdin.read()
+status_lines = []
+for line in text.splitlines():
+    if re.search("^.{4} [\w./].*$", line):
+        status_lines.append(line)
+    elif status_lines:
+        print "\n".join(sorted(status_lines))
+        print line
+        status_lines = []
+    else:
+        print line
+if status_lines:
+    print "\n".join(sorted(status_lines))
+' <"$INPUT_FILE" >"$OUTPUT_FILE"
+}
+
+function check_svn_version() {
+    if ! svn --version | head -1 | grep -q "^svn, version 1.8"; then
+        skip_all "Tests require Subversion 1.8"
+        exit 0
+    fi
+}
+
 function fcm_make_build_hello_tests() {
     local TEST_KEY=$1
     local HELLO_EXT=${2:-}
@@ -200,12 +274,6 @@ __OUT__
 FCM_HOME=${FCM_HOME:-$(cd $(dirname $(readlink -f $BASH_SOURCE))/../../.. && pwd)}
 export FCM_HOME
 PATH=$FCM_HOME/bin:$PATH
-SVN_VERSION_IS_16=false
-SVN_VERSION=$(svn --version)
-if [[ $(echo $SVN_VERSION | head -1 | grep "^svn, version 1.6") ]]; then
-    SVN_VERSION_IS_16=true
-fi
-unset SVN_VERSION
 
 TEST_KEY_BASE=$(basename $0 .t)
 TEST_SOURCE_DIR=$(cd $(dirname $0) && pwd)
diff --git a/t/svn-hooks/00-pre-revprop-change.t b/t/svn-hooks/00-pre-revprop-change.t
index a97e9eb..78572e5 100755
--- a/t/svn-hooks/00-pre-revprop-change.t
+++ b/t/svn-hooks/00-pre-revprop-change.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/svn-hooks/01-post-revprop-change-bg.t b/t/svn-hooks/01-post-revprop-change-bg.t
index 1d28961..1861d78 100755
--- a/t/svn-hooks/01-post-revprop-change-bg.t
+++ b/t/svn-hooks/01-post-revprop-change-bg.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/svn-hooks/02-pre-commit.t b/t/svn-hooks/02-pre-commit.t
index 2194919..f62cb41 100755
--- a/t/svn-hooks/02-pre-commit.t
+++ b/t/svn-hooks/02-pre-commit.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -244,6 +244,7 @@ rm README
 for KEY in $USER Share Config Rel; do
     test_tidy
     TEST_KEY="$TEST_KEY_BASE-branch-owner-$KEY"
+    echo 'verify-branch-owner' >"$REPOS_PATH/hooks/commit.conf"
     run_pass "$TEST_KEY" svn cp --parents -m "$TEST_KEY" \
         "$REPOS_URL/hello/trunk" "$REPOS_URL/hello/branches/dev/$KEY/whatever"
     run_fail "$TEST_KEY.pre-commit.log" test -s "$REPOS_PATH/log/pre-commit.log"
@@ -252,6 +253,7 @@ done
 # Branch create owner verify, bad
 test_tidy
 TEST_KEY="$TEST_KEY_BASE-branch-owner-bad"
+echo 'verify-branch-owner' >"$REPOS_PATH/hooks/commit.conf"
 run_fail "$TEST_KEY" svn cp --parents -m "$TEST_KEY" \
     "$REPOS_URL/hello/trunk" "$REPOS_URL/hello/branches/dev/nosuchuser/whatever"
 TXN=$(<txn)
@@ -279,7 +281,6 @@ __LOG__
 # Branch create owner no verify, bad
 test_tidy
 TEST_KEY="$TEST_KEY_BASE-branch-owner-no-verify-bad"
-echo 'no-verify-branch-owner' >"$REPOS_PATH/hooks/commit.conf"
 run_pass "$TEST_KEY" svn cp --parents -m "$TEST_KEY" \
     "$REPOS_URL/hello/trunk" "$REPOS_URL/hello/branches/dev/nosuchuser/whatever"
 run_fail "$TEST_KEY.pre-commit.log" test -s "$REPOS_PATH/log/pre-commit.log"
diff --git a/t/svn-hooks/03-post-commit-bg.t b/t/svn-hooks/03-post-commit-bg.t
index d596f83..d63d9f9 100755
--- a/t/svn-hooks/03-post-commit-bg.t
+++ b/t/svn-hooks/03-post-commit-bg.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -37,7 +37,7 @@ test_tidy() {
         mail.out
 }
 #-------------------------------------------------------------------------------
-tests 32
+tests 38
 #-------------------------------------------------------------------------------
 cp -p "$FCM_HOME/etc/svn-hooks/post-commit" "$REPOS_PATH/hooks/"
 sed -i "/set -eu/a\
@@ -54,8 +54,10 @@ date2datefmt "$REPOS_PATH/log/post-commit.log" \
     >"$TEST_KEY.log"
 file_cmp "$TEST_KEY.log" "$TEST_KEY.log" <<__LOG__
 YYYY-mm-ddTHH:MM:SSZ+ $REV by $USER
-svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip 1>$PWD/svn-dumps/foo-$REV.gz
+svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip \\
+    | (dd 'conv=fsync' "of=$PWD/svn-dumps/foo-$REV-tmp.gz" 2>/dev/null)
 * Dumped revision $REV.
+mv "$PWD/svn-dumps/foo-$REV-tmp.gz" "$PWD/svn-dumps/foo-$REV.gz"
 REV_FILE_SIZE=??? # within 1048576
 RET_CODE=0
 __LOG__
@@ -65,7 +67,6 @@ if [[ -n ${TRAC_ENV_PATH:-} ]] && ! $TRAC_RESYNC; then
         >"$TEST_KEY.trac.db.expected"
     file_cmp "$TEST_KEY.trac.db" \
         "$TEST_KEY.trac.db.expected" <<<"$REV|$TEST_KEY"
-    cat "$TEST_KEY.trac.db.expected"
 else
     skip 1 '"trac-admin changeset added" not available'
 fi
@@ -90,8 +91,10 @@ __CONF__
         >"$TEST_KEY.log"
     file_cmp "$TEST_KEY.log" "$TEST_KEY.log" <<__LOG__
 YYYY-mm-ddTHH:MM:SSZ+ $REV by $USER
-svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip 1>$PWD/svn-dumps/foo-$REV.gz
+svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip \\
+    | (dd 'conv=fsync' "of=$PWD/svn-dumps/foo-$REV-tmp.gz" 2>/dev/null)
 * Dumped revision $REV.
+mv "$PWD/svn-dumps/foo-$REV-tmp.gz" "$PWD/svn-dumps/foo-$REV.gz"
 REV_FILE_SIZE=??? # within 1048576
 svnlook cat $REPOS_PATH ${NAME} >$REPOS_PATH/hooks/${NAME}
 RET_CODE=0
@@ -116,8 +119,10 @@ __CONF__
         >"$TEST_KEY.log"
     file_cmp "$TEST_KEY.log" "$TEST_KEY.log" <<__LOG__
 YYYY-mm-ddTHH:MM:SSZ+ $REV by $USER
-svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip 1>$PWD/svn-dumps/foo-$REV.gz
+svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip \\
+    | (dd 'conv=fsync' "of=$PWD/svn-dumps/foo-$REV-tmp.gz" 2>/dev/null)
 * Dumped revision $REV.
+mv "$PWD/svn-dumps/foo-$REV-tmp.gz" "$PWD/svn-dumps/foo-$REV.gz"
 REV_FILE_SIZE=??? # within 1048576
 svnlook cat $REPOS_PATH ${NAME} >$REPOS_PATH/hooks/${NAME}
 RET_CODE=0
@@ -136,8 +141,10 @@ __LOG__
         >"$TEST_KEY.log"
     file_cmp "$TEST_KEY.log" "$TEST_KEY.log" <<__LOG__
 YYYY-mm-ddTHH:MM:SSZ+ $REV by $USER
-svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip 1>$PWD/svn-dumps/foo-$REV.gz
+svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip \\
+    | (dd 'conv=fsync' "of=$PWD/svn-dumps/foo-$REV-tmp.gz" 2>/dev/null)
 * Dumped revision $REV.
+mv "$PWD/svn-dumps/foo-$REV-tmp.gz" "$PWD/svn-dumps/foo-$REV.gz"
 REV_FILE_SIZE=??? # within 1048576
 rm -f $REPOS_PATH/hooks/${NAME}
 RET_CODE=0
@@ -156,8 +163,10 @@ date2datefmt "$REPOS_PATH/log/post-commit.log" \
     >"$TEST_KEY.log"
 file_cmp "$TEST_KEY.log" "$TEST_KEY.log" <<__LOG__
 YYYY-mm-ddTHH:MM:SSZ+ $REV by $USER
-svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip 1>$PWD/svn-dumps/foo-$REV.gz
+svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip \\
+    | (dd 'conv=fsync' "of=$PWD/svn-dumps/foo-$REV-tmp.gz" 2>/dev/null)
 * Dumped revision $REV.
+mv "$PWD/svn-dumps/foo-$REV-tmp.gz" "$PWD/svn-dumps/foo-$REV.gz"
 REV_FILE_SIZE=??? # EXCEED 1048576
 RET_CODE=1
 __LOG__
@@ -167,8 +176,10 @@ date2datefmt mail.out \
 file_cmp "$TEST_KEY.mail.out" "$TEST_KEY.mail.out" <<__LOG__
 -s [post-commit-bg] $REPOS_PATH@$REV fcm.admin.team
 YYYY-mm-ddTHH:MM:SSZ+ $REV by $USER
-svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip 1>$PWD/svn-dumps/foo-$REV.gz
+svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip \\
+    | (dd 'conv=fsync' "of=$PWD/svn-dumps/foo-$REV-tmp.gz" 2>/dev/null)
 * Dumped revision $REV.
+mv "$PWD/svn-dumps/foo-$REV-tmp.gz" "$PWD/svn-dumps/foo-$REV.gz"
 REV_FILE_SIZE=??? # EXCEED 1048576
 RET_CODE=1
 __LOG__
@@ -190,8 +201,10 @@ date2datefmt "$REPOS_PATH/log/post-commit.log" \
     >"$TEST_KEY.log"
 file_cmp "$TEST_KEY.log" "$TEST_KEY.log" <<__LOG__
 YYYY-mm-ddTHH:MM:SSZ+ $REV by $USER
-svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip 1>$PWD/svn-dumps/foo-$REV.gz
+svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip \\
+    | (dd 'conv=fsync' "of=$PWD/svn-dumps/foo-$REV-tmp.gz" 2>/dev/null)
 * Dumped revision $REV.
+mv "$PWD/svn-dumps/foo-$REV-tmp.gz" "$PWD/svn-dumps/foo-$REV.gz"
 REV_FILE_SIZE=??? # within 1048576
 $REPOS_PATH/hooks/post-commit-bg-custom $REPOS_PATH $REV $TXN
 $REPOS_PATH $REV $TXN
@@ -217,8 +230,10 @@ date2datefmt "$REPOS_PATH/log/post-commit.log" \
     >"$TEST_KEY.log"
 file_cmp "$TEST_KEY.log" "$TEST_KEY.log" <<__LOG__
 YYYY-mm-ddTHH:MM:SSZ+ $REV by $USER
-svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip 1>$PWD/svn-dumps/foo-$REV.gz
+svnadmin dump -r$REV --incremental --deltas $REPOS_PATH | gzip \\
+    | (dd 'conv=fsync' "of=$PWD/svn-dumps/foo-$REV-tmp.gz" 2>/dev/null)
 * Dumped revision $REV.
+mv "$PWD/svn-dumps/foo-$REV-tmp.gz" "$PWD/svn-dumps/foo-$REV.gz"
 REV_FILE_SIZE=??? # within 1048576
 $REPOS_PATH/hooks/post-commit-background-custom $REPOS_PATH $REV $TXN
 I have gone to the dark side.
@@ -233,6 +248,7 @@ poll 10 grep -q '^RET_CODE=' "$REPOS_PATH/log/post-commit.log"
 
 TEST_KEY="$TEST_KEY_BASE-branch-create-owner-1" # create author is owner
 test_tidy
+echo 'notify-owner' >"${REPOS_PATH}/hooks/commit.conf"
 svn cp -q -m '' --parents \
     "$REPOS_URL/hello/trunk" \
     "$REPOS_URL/hello/branches/dev/$USER/whatever"
@@ -241,6 +257,7 @@ run_fail "$TEST_KEY.mail.out" test -s mail.out
 
 TEST_KEY="$TEST_KEY_BASE-branch-create-owner-2" # create author not owner
 test_tidy
+echo 'notify-owner' >"${REPOS_PATH}/hooks/commit.conf"
 svn cp -q -m '' --parents \
     --username=root \
     --no-auth-cache \
@@ -254,7 +271,6 @@ file_grep "$TEST_KEY.mail.out.2" "^r${REV} | root" mail.out
 
 TEST_KEY="$TEST_KEY_BASE-branch-create-owner-3" # same as 2, but no notify
 test_tidy
-echo 'no-notify-branch-owner' >"${REPOS_PATH}/hooks/commit.conf"
 svn cp -q -m '' --parents \
     --username=root \
     --no-auth-cache \
@@ -265,6 +281,7 @@ run_fail "$TEST_KEY.mail.out" test -s mail.out
 
 TEST_KEY="$TEST_KEY_BASE-branch-modify-owner-1" # modify author is owner
 test_tidy
+echo 'notify-owner' >"${REPOS_PATH}/hooks/commit.conf"
 svn co -q "$REPOS_URL/hello/branches/dev/$USER/whatever" hello
 echo 'Hello Earth' >hello/file
 svn ci -q -m'Hello Earth' hello/file
@@ -273,6 +290,7 @@ run_fail "$TEST_KEY.mail.out" test -s mail.out
 
 TEST_KEY="$TEST_KEY_BASE-branch-modify-owner-2" # modify author not owner
 test_tidy
+echo 'notify-owner' >"${REPOS_PATH}/hooks/commit.conf"
 #svn co -q "$REPOS_URL/hello/branches/dev/$USER/whatever" hello
 echo 'Hello Alien' >hello/file
 svn ci -q -m'Hello Earth' --username=root --no-auth-cache hello/file
@@ -282,14 +300,43 @@ file_grep "$TEST_KEY.mail.out.1" \
     "^-rnotifications at localhost -sfoo@${REV} by root" mail.out
 file_grep "$TEST_KEY.mail.out.2" "^r${REV} | root" mail.out
 
+TEST_KEY="$TEST_KEY_BASE-share-branch-owner-1" # modify share author is owner
+test_tidy
+echo 'notify-owner' >"${REPOS_PATH}/hooks/commit.conf"
+svn cp -q -m '' --parents \
+    "$REPOS_URL/hello/trunk" \
+    "$REPOS_URL/hello/branches/dev/Share/whatever"
+poll 10 grep -q '^RET_CODE=' "$REPOS_PATH/log/post-commit.log"
+run_fail "$TEST_KEY.create.mail.out" test -s mail.out
+test_tidy
+echo 'Greet Alien' >'greet.txt'
+svn import -q -m '' 'greet.txt' \
+    "$REPOS_URL/hello/branches/dev/Share/whatever/greet.txt"
+poll 10 grep -q '^RET_CODE=' "$REPOS_PATH/log/post-commit.log"
+run_fail "$TEST_KEY.modify.mail.out" test -s mail.out
+
+TEST_KEY="$TEST_KEY_BASE-share-branch-owner-2" # modify share author not owner
+test_tidy
+echo 'notify-owner' >"${REPOS_PATH}/hooks/commit.conf"
+echo 'Hail Alien' >'hail.txt'
+svn import -q -m '' --username=root --no-auth-cache 'hail.txt' \
+    "$REPOS_URL/hello/branches/dev/Share/whatever/hail.txt"
+poll 10 grep -q '^RET_CODE=' "$REPOS_PATH/log/post-commit.log"
+REV=$(<rev)
+file_grep "$TEST_KEY.mail.out.1" \
+    "^-rnotifications at localhost -sfoo@${REV} by root" 'mail.out'
+file_grep "$TEST_KEY.mail.out.2" "^r${REV} | root" 'mail.out'
+
 TEST_KEY="$TEST_KEY_BASE-branch-delete-owner-1" # delete author is owner
 test_tidy
+echo 'notify-owner' >"${REPOS_PATH}/hooks/commit.conf"
 svn rm -q -m'No Hello' "$REPOS_URL/hello/branches/dev/$USER/whatever"
 poll 10 grep -q '^RET_CODE=' "$REPOS_PATH/log/post-commit.log"
 run_fail "$TEST_KEY.mail.out" test -s mail.out
 
 TEST_KEY="$TEST_KEY_BASE-branch-delete-owner-2" # delete author not owner
 test_tidy
+echo 'notify-owner' >"${REPOS_PATH}/hooks/commit.conf"
 svn rm -q -m'No Hello' --username=root --no-auth-cache \
     "$REPOS_URL/hello/branches/test/$USER/whatever"
 poll 10 grep -q '^RET_CODE=' "$REPOS_PATH/log/post-commit.log"
@@ -298,4 +345,21 @@ file_grep "$TEST_KEY.mail.out.1" \
     "^-rnotifications at localhost -sfoo@${REV} by root" mail.out
 file_grep "$TEST_KEY.mail.out.2" "^r${REV} | root" mail.out
 #-------------------------------------------------------------------------------
+# Test owner notification
+TEST_KEY="${TEST_KEY_BASE}-owner-1" # trunk author is not owner
+test_tidy
+cat >"${REPOS_PATH}/hooks/commit.conf" <<__CONF__
+notify-owner
+owner = $USER
+__CONF__
+rm -fr 'hello'
+svn co -q "${REPOS_URL}/hello/trunk" 'hello'
+echo 'Hello' >'hello/file'
+svn ci -q -m 'hello whatever' '--no-auth-cache' '--username=root' 'hello'
+poll 10 grep -q '^RET_CODE=' "${REPOS_PATH}/log/post-commit.log"
+REV="$(<rev)"
+file_grep "${TEST_KEY}.mail.out.1" \
+    "^-rnotifications at localhost -sfoo@${REV} by root" 'mail.out'
+file_grep "${TEST_KEY}.mail.out.2" "^r${REV} | root" 'mail.out'
+#-------------------------------------------------------------------------------
 exit
diff --git a/t/svn-hooks/04-svnperms.t b/t/svn-hooks/04-svnperms.t
new file mode 100755
index 0000000..dd4aa31
--- /dev/null
+++ b/t/svn-hooks/04-svnperms.t
@@ -0,0 +1,121 @@
+#!/bin/bash
+#-------------------------------------------------------------------------------
+# (C) British Crown Copyright 2006-15 Met Office.
+#
+# This file is part of FCM, tools for managing and building source code.
+#
+# FCM is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# FCM is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with FCM. If not, see <http://www.gnu.org/licenses/>.
+#-------------------------------------------------------------------------------
+# Basic tests for "pre-commit".
+#-------------------------------------------------------------------------------
+. $(dirname $0)/test_header
+FCM_SVN_HOOK_ADMIN_EMAIL='your.admin.team'
+. $TEST_SOURCE_DIR/test_header_more
+
+svn mkdir --parents $REPOS_URL/foo/trunk -m "create foo trunk"
+svn mkdir --parents $REPOS_URL/foo/branches -m "create foo branches"
+svn mkdir --parents $REPOS_URL/bar/trunk -m "create bar trunk"
+svn mkdir --parents $REPOS_URL/bar/branches -m "create bar branches"
+
+test_tidy() {
+    rm -f \
+        "$REPOS_PATH/hooks/pre-commit-custom" \
+        "$REPOS_PATH/hooks/pre-commit-size-threshold.conf" \
+        "$REPOS_PATH/hooks/commit.conf" \
+        "$REPOS_PATH/hooks/svnperms.conf" \
+        "$REPOS_PATH/log/pre-commit.log" \
+        README \
+        bin/svnperms.py \
+        file1 \
+        file2 \
+        file3 \
+        file4 \
+        mail.out \
+        pre-commit-custom.out \
+        svnperms.py.out
+}
+#-------------------------------------------------------------------------------
+tests 9
+#-------------------------------------------------------------------------------
+cp -p "$FCM_HOME/etc/svn-hooks/pre-commit" "$REPOS_PATH/hooks/"
+sed -i "/set -eu/a\
+echo \$2 >$PWD/txn" "$REPOS_PATH/hooks/pre-commit"
+#-------------------------------------------------------------------------------
+cp "$FCM_HOME/sbin/svnperms.py" "$REPOS_PATH/hooks/"
+REPOS_SHORTNAME=$(basename $REPOS_PATH)
+cat >"$REPOS_PATH/hooks/svnperms.conf" <<__CONF__
+[$REPOS_SHORTNAME groups]
+admin = barry bazzy quxxy xyzzy wibbley
+users = wibbley wobbley wubbley $LOGNAME
+
+[$REPOS_SHORTNAME]
+.* = @admin(add,remove,update)
+
+foo/trunk/.* = @admin(add,remove,update)
+foo/branches/[^/]+/.* = *(add,remove,update)
+foo/tags/[^/]+/.* = @admin(add,remove,update)
+
+bar/trunk/.* = @users(add,remove,update)
+bar/branches/[^/]+/.* = @users(add,remove,update)
+bar/tags/[^/]+/.* = @admin(add,remove,update)
+
+[something_else_svn groups]
+admin = $LOGNAME whoever
+somepeople = bla blubb blabla
+
+[something_else_svn]
+foo/trunk/.* = @admin(add,remove,update)
+foo/branches/[^/]+/.* = @somepeople(add,remove,update)
+foo/tags/[^/]+/.* = @admin(add,remove,update)
+__CONF__
+touch file1
+#-------------------------------------------------------------------------------
+TEST_KEY="$TEST_KEY_BASE-trunk-fail"
+run_fail "$TEST_KEY" \
+    svn import --no-auth-cache -q -m'test' file1 "$REPOS_URL/foo/trunk/file1"
+file_grep "$TEST_KEY.foo-trunk.err" \
+    "error: you don't have enough permissions for this transaction:" \
+    "$TEST_KEY.err"
+#-------------------------------------------------------------------------------
+TEST_KEY="$TEST_KEY_BASE-trunk-fail-custom-err-message"
+echo "
+[message]
+permerrors_prefix = Bad User!" >>"$REPOS_PATH/hooks/svnperms.conf"
+run_fail "$TEST_KEY" \
+    svn import --no-auth-cache -q -m'test' file1 "$REPOS_URL/foo/trunk/file1"
+file_grep "$TEST_KEY.foo-trunk.err" "Bad User!" "$TEST_KEY.err"
+#-------------------------------------------------------------------------------
+TEST_KEY="$TEST_KEY_BASE-trunk-fail-custom-err-message-repos"
+echo "
+[$REPOS_SHORTNAME message]
+permerrors_prefix = FCM police notified" >>"$REPOS_PATH/hooks/svnperms.conf"
+run_fail "$TEST_KEY" \
+    svn import --no-auth-cache -q -m'test' file1 "$REPOS_URL/foo/trunk/file1"
+file_grep "$TEST_KEY.foo-trunk.err" "FCM police notified" "$TEST_KEY.err"
+#-------------------------------------------------------------------------------
+TEST_KEY="$TEST_KEY_BASE-branch-pass-all"
+run_pass "$TEST_KEY" \
+    svn mkdir --parents --no-auth-cache -q -m 'test' \
+    "$REPOS_URL/foo/branches/dev/$LOGNAME/"$(date +%s.%N)
+#-------------------------------------------------------------------------------
+TEST_KEY="$TEST_KEY_BASE-trunk-pass"
+run_pass "$TEST_KEY" \
+    svn import --no-auth-cache -q -m'test' file1 "$REPOS_URL/bar/trunk/file1"
+#-------------------------------------------------------------------------------
+TEST_KEY="$TEST_KEY_BASE-branch-pass-group"
+run_pass "$TEST_KEY" \
+    svn mkdir --parents --no-auth-cache -q -m 'test' \
+    "$REPOS_URL/bar/branches/dev/$LOGNAME/"$(date +%s.%N)
+#-------------------------------------------------------------------------------
+exit
diff --git a/t/svn-hooks/test_header_more b/t/svn-hooks/test_header_more
index 78ec710..3399a79 100644
--- a/t/svn-hooks/test_header_more
+++ b/t/svn-hooks/test_header_more
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
@@ -91,6 +91,11 @@ then
     else
         TRAC_RESYNC=false
     fi
+    cat >>"${TRAC_ENV_PATH}/conf/trac.ini" <<'__TRAC_INI___'
+
+[components]
+tracopt.versioncontrol.svn.* = enabled
+__TRAC_INI___
 fi
 unset ADMIN_DIR
 cat >bin/mail <<__BASH__
diff --git a/t/svn-username/00-branch.t b/t/svn-username/00-branch.t
index 02b2edd..96f280c 100755
--- a/t/svn-username/00-branch.t
+++ b/t/svn-username/00-branch.t
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/t/svn-username/test_header b/t/svn-username/test_header
index 672ce12..6d52eac 100644
--- a/t/svn-username/test_header
+++ b/t/svn-username/test_header
@@ -1,6 +1,6 @@
 #!/bin/bash
 # ------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/tutorial/fcm-tutorial-repos-create b/tutorial/fcm-tutorial-repos-create
index 93996d8..f7ef3a8 100755
--- a/tutorial/fcm-tutorial-repos-create
+++ b/tutorial/fcm-tutorial-repos-create
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #
diff --git a/usr/bin/fcm b/usr/bin/fcm
index 665112b..1843a22 100755
--- a/usr/bin/fcm
+++ b/usr/bin/fcm
@@ -1,6 +1,6 @@
 #!/bin/bash
 #-------------------------------------------------------------------------------
-# (C) British Crown Copyright 2006-14 Met Office.
+# (C) British Crown Copyright 2006-15 Met Office.
 #
 # This file is part of FCM, tools for managing and building source code.
 #

-- 
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/debian-science/packages/fcm.git



More information about the debian-science-commits mailing list