dbc9f6aea991 introduced "svn info TARGET@REV" to determine if a certain
path exists in the specified revision, but in svn 1.5 the error message
"Not a valid URL" yields exit code 0 so the error is not caught.
Use "svn list TARGET@REV" instead which works with svn 1.5 and is even
faster in some situations.
Another version could have returned a revset expression from
getoutgoing(), but we do not know how many times it will be resolved, so
better do it once explicitely.
`extinct` changesets are obsolete changesets with obsolete descendants only. They
are of no interest anymore and can be:
- exclude from exchange
- hidden to the user in most situation
- safely garbage collected
This changeset just allows mercurial to detect them.
The implementation is a bit naive, as for unstable changesets. We better use a
simple revset query and a cache, but simple version comes first.
User should resolve unstability locally before pushing the same way we encourage
user to merge locally instead of pushing a new remote head.
If we are to push obsolete changeset, at least one set of the pushed set will be
either obsolete or unstable. The check is narrowed to only heads.
An unstable changeset is a changeset *not* obsolete but with some obsolete
ancestors.
The current logic to decide if a changeset is unstable is naive and very
inefficient. A better solution is to compute the set of unstable changeset with
a simple revset and to cache the result. But this require cache invalidation
logic. Simpler version goes first.
Some compilers / compiler options (such as gcc 4.7) would emit warnings:
mercurial/parsers.c: In function 'pack_dirstate':
mercurial/parsers.c:306:18: warning: 'size' may be used uninitialized in this function [-Wmaybe-uninitialized]
mercurial/parsers.c:306:12: warning: 'mode' may be used uninitialized in this function [-Wmaybe-uninitialized]
It is apparently not smart enough to figure out how the 'err' arithmetics makes
sure that it can't happen.
'err' is now replaced with simple checks and goto. That might also help the
optimizer when it is inlining getintat().
It was introduced by c094f330c014, returned by asciiformat() but never
read anywhere. 0997c9dc5951 stopped using it completely, and the
graphmod.CHANGESET type is passed through all functions.
As a part of migration to vfs, this patch invokes some file API
indirectly via vfs, while ensuring repository directory in the
constructor of "localrepository" class.
New file API are added to "scmutil.abstractopener" class, because they
are also used via other derived classes than "scmutil.opener".
But "join()" is not yet defined other than "scmutil.opener" class,
because it should not be used via other opener classes yet.
As a part of migration to vfs, this patch uses "self.vfs" instead of
"self.opener", while ensuring repository directory in the constructor
of "localrepository" class.
As a part of migration to vfs, this patch uses "self.root", which can
be recognized as the path relative to "self.vfs", instead of "path"
argument.
This fix allows to make invocations of "util.makedirs()" and
"os.path.exists()" while ensuring repository directory in
"localrepository.__init__()" ones indirectly via vfs.
But this fix also raises issue 2528: "hg clone" with empty destination.
"path" argument is empty in many cases, so this issue can't be fixed
in the view of "localrepository.__init__()".
Before this patch, it is fixed by empty-ness check ("not name") of
exception handler in "util.makedirs()".
try:
os.mkdir(name)
except OSError, err:
if err.errno == errno.EEXIST:
return
if err.errno != errno.ENOENT or not name:
raise
This requires "localrepository.__init__()" to invoke "util.makedirs()"
with "path" instead of "self.root", because empty "path" is treated as
"current directory" and "self.root" becomes valid path.
But "hg clone" with empty destination can be detected also in
"hg.clone()" before "localrepository.__init__()" invocation, so this
patch re-fixes issue2528 by checking it in "hg.clone()".
As a part of migration to vfs, this patch uses "self.wvfs.join()"
instead of "os.path.join()", while initialization of fields in the
constructor of "localrepository" class.
As a part of migration to vfs, this patch moves path expansion API
invocations in the constructor of "localrepository" to the constructor
of "opener", because the root path to the repository is very important
to handle paths using non-ASCII characters correctly.
This patch also rearrange initialization order of "wvfs" field,
because it is required to initialize "self.root".
As a part of migration to vfs, this patch adds "vfs" fields to
"localrepository" class.
This allows new codes to access current "opener" objects related to
repositories via "vfs" fields, so patches referring to "vfs" will
replace referring to "opener" in time.
This patch also adds initializations for "vfs" fields to
"statichttprepository" class derived from it, because its constructor
doesn't invoke the constructor of "localrepository", so "vfs" fields
should be initialized explicitly as same as "opener" fields: it has no
working directory, so "wvfs" field is not added.
This speeds up status on a largefiles repo by synchronizing the largefiles dirstate to the
largefile's mtime upon update, preventing the files from coming back as "unsure" later,
requiring a check of the SHA1 sum.
Before this patch, MQ checks each subrepo synchronizations against the
working directory context, so ".hgsubstate" updating is not imported
into MQ revision correctly in cases below:
- qrefresh when current ".hgsubstate" is already synchronized with
each subrepos: you can reproduce this easily by just twice or more
qrefresh invocations
- qnew just after rollback of commit which updates ".hgsubstate"
This patch resolves this by checking subrepo states against:
- the parent of "qtop" for qrefresh, or
- the parent of working context otherwise
Even though the committed revision contains diff of ".hgsubstate", the
patch file created by qrefresh doesn't contain it, because:
- ".hgsubstate" is not listed up as one of target files of the patch
for reasons below, so diff of ".hgsubstate" is not imported into
patch file
- status of ".hgsubstate" in working directory is usually "clean"
- ".hgsubstate" is not specified explicitly by users
- the patch file is created before commit processing which updates
or creates ".hgsubstate" automatically, so there is no diff for it
at that time
This patch resolves this problem by:
- putting ".hgsubstate" into target list of the patch, if needed:
this allows "patch.diff()" to import diff of ".hgsubstate" into
patch file.
- creating the patch file after commit processing:
this updates ".hgsubstate" before "patch.diff()" invocation.
For the former fixing, this patch introduces "putsubstate2changes()"
to share same implementation with qnew. This is invoked only once per
qnew/qrefresh at most, so there is less performance impact.
This patch also omits "match" argument for "patch.diff()" invocation,
because "patch.diff()" ignores "match" if "changes" is specified.
If ".hgsubstate" is already listed up as one of commit targets, qnew
put diff of ".hgsubstate" twice into the patch file stored under
".hg/patches".
It causes rejections at applying such patches.
Other than the case like in added test script, this can also occur
when qnew is executed just after rolling back the committing updated
".hgsubstate".
This patch checks whether ".hgsubstate" is already listed up as one of
commit targets, and put it into the appropriate list only if it is not
listed up yet.