Patchwork [STABLE] patch: don't separate \r and \n when colorizing diff output

login
register
mail settings
Submitter via Mercurial-devel
Date July 10, 2018, 11:20 a.m.
Message ID <37b29ae6598324a8079f.1531221634@firefly.edlund.dk>
Download mbox | patch
Permalink /patch/32732/
State Accepted
Headers show

Comments

via Mercurial-devel - July 10, 2018, 11:20 a.m.
# HG changeset patch
# User Sune Foldager <cryo@cyanite.org>
# Date 1531221514 -7200
#      Tue Jul 10 13:18:34 2018 +0200
# Branch stable
# Node ID 37b29ae6598324a8079f1d6d0cb973068a628ab7
# Parent  3a0f322af1926e52322d2cff90a71529f359f2d9
patch: don't separate \r and \n when colorizing diff output

When displaying diffs, \r at the end of a line is treated as trailing
whitespace. This causes an ANSI escape code to be inserted between \r and \n.
Some programs, such as less since version 530 (maybe earlier, but at least not
version 487) displays ^M when it encounters a lone \r. This causes a lot of
noise in diff output on Windows, where \r\n is used to terminate lines.

We avoid that by treating both \n and \r\n as end of line when considering
trailing whitespace.
Yuya Nishihara - July 10, 2018, 12:54 p.m.
On Tue, 10 Jul 2018 13:20:34 +0200, Sune Foldager via Mercurial-devel wrote:
> # HG changeset patch
> # User Sune Foldager <cryo@cyanite.org>
> # Date 1531221514 -7200
> #      Tue Jul 10 13:18:34 2018 +0200
> # Branch stable
> # Node ID 37b29ae6598324a8079f1d6d0cb973068a628ab7
> # Parent  3a0f322af1926e52322d2cff90a71529f359f2d9
> patch: don't separate \r and \n when colorizing diff output

Queued for default since it's close to freeze and this isn't a critical issue.
Thanks. Can you add some tests as a follow up?

FWIW I miss this bug which helped me to notice unwanted CRLF line ending.

Patch

diff --git a/mercurial/patch.py b/mercurial/patch.py
--- a/mercurial/patch.py
+++ b/mercurial/patch.py
@@ -2489,7 +2489,7 @@  def diffsinglehunk(hunklines):
     """yield tokens for a list of lines in a single hunk"""
     for line in hunklines:
         # chomp
-        chompline = line.rstrip('\n')
+        chompline = line.rstrip('\r\n')
         # highlight tabs and trailing whitespace
         stripline = chompline.rstrip()
         if line[0] == '-':
@@ -2557,6 +2557,9 @@  def diffsinglehunkinline(hunklines):
             isendofline = token.endswith('\n')
             if isendofline:
                 chomp = token[:-1] # chomp
+                if chomp.endswith('\r'):
+                    chomp = chomp[:-1]
+                endofline = token[len(chomp):]
                 token = chomp.rstrip() # detect spaces at the end
                 endspaces = chomp[len(token):]
             # scan tabs
@@ -2572,7 +2575,7 @@  def diffsinglehunkinline(hunklines):
             if isendofline:
                 if endspaces:
                     yield (endspaces, 'diff.trailingwhitespace')
-                yield ('\n', '')
+                yield (endofline, '')
                 nextisnewline = True
 
 def difflabel(func, *args, **kw):