mercurial/diffhelper.py
author Martin von Zweigbergk <martinvonz@google.com>
Mon, 07 May 2018 14:32:43 -0700
changeset 37866 37e7ae332e90
parent 37836 86e7a57449fa
child 38783 e7aa113b14f7
permissions -rw-r--r--
revset: make id() an empty set for ambiguous nodeid (BC) As Yuya pointed out in the review of D3311, id() (and rev()) does not raise an error when the input is an unknown identifier, so it doesn't make sense for it to do that when the input is ambiguous with a filtered node. However, it turned out that it already does raise an error when the input is ambiguous among the visible nodes. So let's start by fixing that. Differential Revision: https://phab.mercurial-scm.org/D3462
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
37803
72f6498c040b diffhelper: rename module to avoid conflicts with ancient C module (issue5846)
Yuya Nishihara <yuya@tcha.org>
parents: 37802
diff changeset
     1
# diffhelper.py - helper routines for patch
7702
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
     2
#
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
     3
# Copyright 2009 Matt Mackall <mpm@selenic.com> and others
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
     4
#
8225
46293a0c7e9f updated license to be explicit about GPL version 2
Martin Geisler <mg@lazybytes.net>
parents: 7702
diff changeset
     5
# This software may be used and distributed according to the terms of the
10263
25e572394f5c Update license to GPLv2+
Matt Mackall <mpm@selenic.com>
parents: 8225
diff changeset
     6
# GNU General Public License version 2 or any later version.
7702
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
     7
27336
80214358ac88 diffhelpers: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 12387
diff changeset
     8
from __future__ import absolute_import
80214358ac88 diffhelpers: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 12387
diff changeset
     9
37573
49b82cdb5983 patch: error out if reached to EOF while reading hunk
Yuya Nishihara <yuya@tcha.org>
parents: 37572
diff changeset
    10
from .i18n import _
49b82cdb5983 patch: error out if reached to EOF while reading hunk
Yuya Nishihara <yuya@tcha.org>
parents: 37572
diff changeset
    11
49b82cdb5983 patch: error out if reached to EOF while reading hunk
Yuya Nishihara <yuya@tcha.org>
parents: 37572
diff changeset
    12
from . import (
49b82cdb5983 patch: error out if reached to EOF while reading hunk
Yuya Nishihara <yuya@tcha.org>
parents: 37572
diff changeset
    13
    error,
49b82cdb5983 patch: error out if reached to EOF while reading hunk
Yuya Nishihara <yuya@tcha.org>
parents: 37572
diff changeset
    14
)
49b82cdb5983 patch: error out if reached to EOF while reading hunk
Yuya Nishihara <yuya@tcha.org>
parents: 37572
diff changeset
    15
7702
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    16
def addlines(fp, hunk, lena, lenb, a, b):
37567
53021c4ef0b2 diffhelpers: port docstrings from cext to pure
Yuya Nishihara <yuya@tcha.org>
parents: 37566
diff changeset
    17
    """Read lines from fp into the hunk
53021c4ef0b2 diffhelpers: port docstrings from cext to pure
Yuya Nishihara <yuya@tcha.org>
parents: 37566
diff changeset
    18
53021c4ef0b2 diffhelpers: port docstrings from cext to pure
Yuya Nishihara <yuya@tcha.org>
parents: 37566
diff changeset
    19
    The hunk is parsed into two arrays, a and b. a gets the old state of
53021c4ef0b2 diffhelpers: port docstrings from cext to pure
Yuya Nishihara <yuya@tcha.org>
parents: 37566
diff changeset
    20
    the text, b gets the new state. The control char from the hunk is saved
53021c4ef0b2 diffhelpers: port docstrings from cext to pure
Yuya Nishihara <yuya@tcha.org>
parents: 37566
diff changeset
    21
    when inserting into a, but not b (for performance while deleting files.)
53021c4ef0b2 diffhelpers: port docstrings from cext to pure
Yuya Nishihara <yuya@tcha.org>
parents: 37566
diff changeset
    22
    """
7702
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    23
    while True:
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    24
        todoa = lena - len(a)
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    25
        todob = lenb - len(b)
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    26
        num = max(todoa, todob)
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    27
        if num == 0:
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    28
            break
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    29
        for i in xrange(num):
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    30
            s = fp.readline()
37573
49b82cdb5983 patch: error out if reached to EOF while reading hunk
Yuya Nishihara <yuya@tcha.org>
parents: 37572
diff changeset
    31
            if not s:
49b82cdb5983 patch: error out if reached to EOF while reading hunk
Yuya Nishihara <yuya@tcha.org>
parents: 37572
diff changeset
    32
                raise error.ParseError(_('incomplete hunk'))
7702
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    33
            if s == "\\ No newline at end of file\n":
37570
c4c8d0d1267f diffhelpers: naming and whitespace cleanup
Yuya Nishihara <yuya@tcha.org>
parents: 37567
diff changeset
    34
                fixnewline(hunk, a, b)
7702
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    35
                continue
37575
230eb9594150 diffhelpers: be more tolerant for stripped empty lines of CRLF ending
Yuya Nishihara <yuya@tcha.org>
parents: 37574
diff changeset
    36
            if s == '\n' or s == '\r\n':
7702
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    37
                # Some patches may be missing the control char
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    38
                # on empty lines. Supply a leading space.
37575
230eb9594150 diffhelpers: be more tolerant for stripped empty lines of CRLF ending
Yuya Nishihara <yuya@tcha.org>
parents: 37574
diff changeset
    39
                s = ' ' + s
7702
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    40
            hunk.append(s)
37566
f53b55b162f4 py3: get rid of character access from pure.diffhelpers
Yuya Nishihara <yuya@tcha.org>
parents: 27336
diff changeset
    41
            if s.startswith('+'):
7702
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    42
                b.append(s[1:])
37566
f53b55b162f4 py3: get rid of character access from pure.diffhelpers
Yuya Nishihara <yuya@tcha.org>
parents: 27336
diff changeset
    43
            elif s.startswith('-'):
7702
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    44
                a.append(s)
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    45
            else:
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    46
                b.append(s[1:])
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    47
                a.append(s)
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    48
37570
c4c8d0d1267f diffhelpers: naming and whitespace cleanup
Yuya Nishihara <yuya@tcha.org>
parents: 37567
diff changeset
    49
def fixnewline(hunk, a, b):
37567
53021c4ef0b2 diffhelpers: port docstrings from cext to pure
Yuya Nishihara <yuya@tcha.org>
parents: 37566
diff changeset
    50
    """Fix up the last lines of a and b when the patch has no newline at EOF"""
7702
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    51
    l = hunk[-1]
10551
f61dced1367a fix test-mq-eol under --pure (mimic diffhelper.c behaviour)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 10263
diff changeset
    52
    # tolerate CRLF in last line
f61dced1367a fix test-mq-eol under --pure (mimic diffhelper.c behaviour)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 10263
diff changeset
    53
    if l.endswith('\r\n'):
f61dced1367a fix test-mq-eol under --pure (mimic diffhelper.c behaviour)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 10263
diff changeset
    54
        hline = l[:-2]
f61dced1367a fix test-mq-eol under --pure (mimic diffhelper.c behaviour)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 10263
diff changeset
    55
    else:
f61dced1367a fix test-mq-eol under --pure (mimic diffhelper.c behaviour)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 10263
diff changeset
    56
        hline = l[:-1]
7702
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    57
37566
f53b55b162f4 py3: get rid of character access from pure.diffhelpers
Yuya Nishihara <yuya@tcha.org>
parents: 27336
diff changeset
    58
    if hline.startswith((' ', '+')):
10551
f61dced1367a fix test-mq-eol under --pure (mimic diffhelper.c behaviour)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 10263
diff changeset
    59
        b[-1] = hline[1:]
37566
f53b55b162f4 py3: get rid of character access from pure.diffhelpers
Yuya Nishihara <yuya@tcha.org>
parents: 27336
diff changeset
    60
    if hline.startswith((' ', '-')):
7702
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    61
        a[-1] = hline
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    62
    hunk[-1] = hline
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    63
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    64
def testhunk(a, b, bstart):
37567
53021c4ef0b2 diffhelpers: port docstrings from cext to pure
Yuya Nishihara <yuya@tcha.org>
parents: 37566
diff changeset
    65
    """Compare the lines in a with the lines in b
53021c4ef0b2 diffhelpers: port docstrings from cext to pure
Yuya Nishihara <yuya@tcha.org>
parents: 37566
diff changeset
    66
53021c4ef0b2 diffhelpers: port docstrings from cext to pure
Yuya Nishihara <yuya@tcha.org>
parents: 37566
diff changeset
    67
    a is assumed to have a control char at the start of each line, this char
53021c4ef0b2 diffhelpers: port docstrings from cext to pure
Yuya Nishihara <yuya@tcha.org>
parents: 37566
diff changeset
    68
    is ignored in the compare.
53021c4ef0b2 diffhelpers: port docstrings from cext to pure
Yuya Nishihara <yuya@tcha.org>
parents: 37566
diff changeset
    69
    """
7702
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    70
    alen = len(a)
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    71
    blen = len(b)
37802
090c89a8db32 diffhelpers: backport 9e40bc4c1bde from C implementation
Yuya Nishihara <yuya@tcha.org>
parents: 37575
diff changeset
    72
    if alen > blen - bstart or bstart < 0:
37574
a1bcc7ff0eac diffhelpers: make return value of testhunk() more Pythonic
Yuya Nishihara <yuya@tcha.org>
parents: 37573
diff changeset
    73
        return False
7702
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    74
    for i in xrange(alen):
f6bb40554e34 pure Python implementation of diffhelpers.c
Martin Geisler <mg@daimi.au.dk>
parents:
diff changeset
    75
        if a[i][1:] != b[i + bstart]:
37574
a1bcc7ff0eac diffhelpers: make return value of testhunk() more Pythonic
Yuya Nishihara <yuya@tcha.org>
parents: 37573
diff changeset
    76
            return False
a1bcc7ff0eac diffhelpers: make return value of testhunk() more Pythonic
Yuya Nishihara <yuya@tcha.org>
parents: 37573
diff changeset
    77
    return True