[PATCH] debug: automate the process of truncating a damaged obsstore

Yuya Nishihara yuya at tcha.org
Sat Jul 2 23:59:31 EDT 2016


On Thu, 30 Jun 2016 07:04:09 -0700, Simon Farnsworth wrote:
> # HG changeset patch
> # User Simon Farnsworth <simonfar at fb.com>
> # Date 1467295436 25200
> #      Thu Jun 30 07:03:56 2016 -0700
> # Node ID 252cefa0326063bd664f47e3628942df30d08ccf
> # Parent  c42a3fd5c1fc5193e5f45887bfddaf05ca977fa4
> debug: automate the process of truncating a damaged obsstore

(issue5265)

> + at command('debugtruncatestore',
> +    [('', 'obsolete', None, _('truncate bad markers in obsstore'))],
> +    _('[OPTION]'))
> +def debugtruncatestore(ui, repo, **opts):
> +    """Fix up repository corruption by truncating damaged files
> +
> +    Most on-disk data structures are designed to be append-only. A failed write
> +    (e.g. due to an unexpected power failure) can leave the file corrupted.
> +
> +    This command attempts to recover from that situation by replacing the
> +    corrupted file with a version that only contains the valid records from the
> +    broken file.
> +
> +    You should normally use :hg:`recover` before resorting to this command.
> +    """
> +
> +    if 'obsolete' in opts:
> +        data = repo.svfs.tryread('obsstore')
> +        if data:
> +            # Slow algorithm - but this is an emergency debug operation
> +            version = None
> +            corrupt = False
> +            while version is None:
> +                try:
> +                    (version, markers) = obsolete._readmarkers(data)
> +                except ValueError:
> +                    corrupt = True
> +                    version = None
> +                    data = data[:-1]
> +                    continue
> +                break
> +            if corrupt:
> +                repo.svfs.write('obsstore', data)
> +                ui.write(_('truncated obsstore\n'))
> +            else:
> +                ui.write(_('no corruption\n'))

It should be covered by a lock. I'm not sure if a transaction is necessary.

And can you add a test? I want to run it with/without --pure to see both
cases are handled well.


More information about the Mercurial-devel mailing list