git/list[1] front-page[2] threads[3] people[4] search[5] about
 

Re: [PATCH] Teach 'git-apply --whitespace=strip' to remove empty lines at the end of file

From
MCMarco Costalba <mcostalba@gmail.com>
Date
May 20, 2007, 12:45 UTC
Message-ID
<e5bfff550705200545kcf1f7f9n4f3f6d7d25955e1@mail.gmail.com>
In-Reply-To
<7vabvzoij8.fsf@assigned-by-dhcp.cox.net>
On 5/20/07, Junio C Hamano <junkio@cox.net> wrote:
Show 8 quoted lines
>
> I was starting to suspect that I misunderstood what you were
> trying to do.  I thought you were trying to avoid a patch that
> adds (one or more) blank line(s) at the end of the file, but is
> it that you do not want to have a hunk that adds more than one
> blank line anywhere?  However, the comment "Only fragments that
> add lines at the bottom ends with '+' lines" suggests otherwise.
>
No, you understand right.
Show 8 quoted lines
>
> Because we had the same mistake in our earlier code as you made
> in this patch, which assumed that a hunk that ends with '+' only
> apply at the end (and we still assume that by default), if you
> apply this with patch git-apply without --unidiff-zero option,
> you get an error.  If you use the option this patch can be
> applied correctly.
>

Ok. This is take 3. It works correctly on standard patches and also on u0 example that you gave above.

This patch is on top of git 1.5.2
Please check it.
builtin-apply.c |   34 ++++++++++++++++++++++++++++++++++
 1 files changed, 34 insertions(+), 0 deletions(-)
diff --git a/builtin-apply.c b/builtin-apply.c
index 0399743..6032f78 100644
--- a/builtin-apply.c
+++ b/builtin-apply.c
@@ -1671,6 +1671,7 @@ static int apply_one_fragment(struct buffer_desc *desc,
 	char *new = xmalloc(size);
 	const char *oldlines, *newlines;
 	int oldsize = 0, newsize = 0;
+	int trailing_added_lines = 0;
 	unsigned long leading, trailing;
 	int pos, lines;

@@ -1699,6 +1700,17 @@ static int apply_one_fragment(struct buffer_desc *desc,
 			else if (first == '+')
 				first = '-';
 		}
+		/*
+		 * Count lines added at the end of the file.
+		 * This is not enough to get things right in case of
+		 * patches generated with --unified=0, but it's a
+		 * useful upper bound.
+		*/
+		if (first == '+')
+			trailing_added_lines++;
+		else
+			trailing_added_lines = 0;
+
 		switch (first) {
 		case '\n':
 			/* Newer GNU diff, empty context line */
@@ -1738,6 +1750,24 @@ static int apply_one_fragment(struct buffer_desc *desc,
 		newsize--;
 	}

+	if (new_whitespace == strip_whitespace) {
+		/* Any added empty lines is already cleaned-up here
+		 * becuase of 'strip_whitespace' flag, so just count '\n'
+		*/
+		int empty = 0;
+		while (   empty < trailing_added_lines
+		       && newsize - empty > 0
+		       && new[newsize - empty - 1] == '\n')
+			empty++;
+
+		if (empty < trailing_added_lines)
+			empty--;
+
+		/* these are the empty lines added at
+		 * the end of the file, modulo u0 patches.
+		 */
+		trailing_added_lines = empty;
+	}
 	oldlines = old;
 	newlines = new;
 	leading = frag->leading;
@@ -1770,6 +1800,10 @@ static int apply_one_fragment(struct buffer_desc *desc,
 		if (match_beginning && offset)
 			offset = -1;
 		if (offset >= 0) {
+
+			if (desc->size - oldsize - offset == 0) /* end of file? */
+				newsize -= trailing_added_lines;
+
 			int diff = newsize - oldsize;
 			unsigned long size = desc->size + diff;
 			unsigned long alloc = desc->alloc;
Previous: Junio C HamanoNext: Junio C Hamano
Message 5 of 16 in “Teach 'git-apply --whitespace=strip' to remove empty lines at the end of file”
  1. Teach 'git-apply --whitespace=strip' to remove empty lines at the end of fileMarco Costalba, May 20, 2007
  2. Junio C HamanoMay 20, 2007
  3. Marco CostalbaMay 20, 2007
  4. Junio C HamanoMay 20, 2007
  5. Marco CostalbaMay 20, 2007
  6. Junio C HamanoMay 20, 2007
  7. Marco CostalbaMay 20, 2007
  8. Junio C HamanoMay 20, 2007
  9. Marco CostalbaMay 20, 2007
  10. Frank LichtenheldMay 20, 2007
  11. Marco CostalbaMay 20, 2007
  12. Josef WeidendorferMay 21, 2007
  13. Junio C HamanoMay 21, 2007
  14. Marco CostalbaMay 21, 2007
  15. Junio C HamanoMay 22, 2007
  16. Marco CostalbaMay 22, 2007

Read the whole thread, see it on lore, or plain text.

$ cat FOOTERMessages come from the public archive at lore.kernel.org/git, fetched every hour. The front page is chosen and written each morning by an AI editor and can be wrong; the threads themselves are the record. About and API. For agents: an MCP server at https://gitlist.dev/mcp, and any thread, story or person page as Markdown by adding .md to its URL (or sending Accept: text/markdown). Details in /llms.txt.