Hi Paul, I'm trying to understand the meaning of 'in_position' and 'out_position' in function 'print_half_line'. While doing this, I spotted a bug:
$ cat foo1.txt a ab abc $ cat foo2.txt ab abcd $ src/diff -t -y foo1.txt foo2.txt a < ab ab abc | abcd This is obviously not how it's intended to be. The attached patch fixes it. The cause is that in the case of a character of width 1, the assignment out_position = in_position; was lost in commit 05cdf3102ef3fb261db311a3e5d090fb63dbc792 (yesterday). With this patch, the result is again as it should be: $ src/diff -t -y foo1.txt foo2.txt a < ab ab abc | abcd The patch also improves comments in this function. So that next time, I (or anyone else) don't spent 30 minutes to understand the difference between 'in_position' and 'out_position'. Bruno
>From 9826aa322e65815288ae63c3a0bb81c1c1267cd8 Mon Sep 17 00:00:00 2001 From: Bruno Haible <br...@clisp.org> Date: Wed, 5 Jul 2023 19:26:52 +0200 Subject: [PATCH] diff: Fix "diff -y" output This fixes a regression from 2023-07-04. * src/side.c (print_half_line): Restore the assignment to out_position. --- src/side.c | 18 ++++++++++++++---- 1 file changed, 14 insertions(+), 4 deletions(-) diff --git a/src/side.c b/src/side.c index 8404c3a..49c7fe5 100644 --- a/src/side.c +++ b/src/side.c @@ -66,14 +66,19 @@ tab_from_to (intmax_t from, intmax_t to) } /* Print the text for half an sdiff line. This means truncate to - width observing tabs, and trim a trailing newline. Return the - last column written (not the number of chars). */ + OUT_BOUND columns, observing tabs, and trim a trailing newline. + Return the presumed column position on the output device after + the write (not the number of chars). */ static intmax_t print_half_line (char const *const *line, intmax_t indent, intmax_t out_bound) { FILE *out = outfile; + /* IN_POSITION is the current column position if we were outputting the + entire line, i.e. ignoring OUT_BOUND. */ intmax_t in_position = 0; + /* OUT_POSITION is the current column position. It stays <= OUT_BOUND + at any moment. */ intmax_t out_position = 0; char const *text_pointer = line[0]; char const *text_limit = line[1]; @@ -188,9 +193,14 @@ print_half_line (char const *const *line, intmax_t indent, intmax_t out_bound) case 'z': case '{': case '|': case '}': case '~': if (ckd_add (&in_position, in_position, 1)) return out_position; - FALLTHROUGH; + if (in_position <= out_bound) + { + out_position = in_position; + putc (c, out); + } + break; - /* Print width already handled. */ + /* Print width 0. */ case '\0': case '\f': case '\v': if (in_position <= out_bound) putc (c, out); -- 2.34.1