kgdb(1): Add missing "
[dragonfly.git] / contrib / diffutils / src / util.c
blob016057d6684a22c891e3d736b517e2edc6f98917
1 /* Support routines for GNU DIFF.
3 Copyright (C) 1988-1989, 1992-1995, 1998, 2001-2002, 2004, 2006, 2009-2013
4 Free Software Foundation, Inc.
6 This file is part of GNU DIFF.
8 This program is free software: you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation, either version 3 of the License, or
11 (at your option) any later version.
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with this program. If not, see <http://www.gnu.org/licenses/>. */
21 #include "diff.h"
22 #include <dirname.h>
23 #include <error.h>
24 #include <system-quote.h>
25 #include <xalloc.h>
26 #include "xvasprintf.h"
28 char const pr_program[] = PR_PROGRAM;
30 /* Queue up one-line messages to be printed at the end,
31 when -l is specified. Each message is recorded with a 'struct msg'. */
33 struct msg
35 struct msg *next;
36 char args[1]; /* Format + 4 args, each '\0' terminated, concatenated. */
39 /* Head of the chain of queues messages. */
41 static struct msg *msg_chain;
43 /* Tail of the chain of queues messages. */
45 static struct msg **msg_chain_end = &msg_chain;
47 /* Use when a system call returns non-zero status.
48 NAME should normally be the file name. */
50 void
51 perror_with_name (char const *name)
53 error (0, errno, "%s", name);
56 /* Use when a system call returns non-zero status and that is fatal. */
58 void
59 pfatal_with_name (char const *name)
61 int e = errno;
62 print_message_queue ();
63 error (EXIT_TROUBLE, e, "%s", name);
64 abort ();
67 /* Print an error message containing MSGID, then exit. */
69 void
70 fatal (char const *msgid)
72 print_message_queue ();
73 error (EXIT_TROUBLE, 0, "%s", _(msgid));
74 abort ();
77 /* Like printf, except if -l in effect then save the message and print later.
78 This is used for things like "Only in ...". */
80 void
81 message (char const *format_msgid, char const *arg1, char const *arg2)
83 message5 (format_msgid, arg1, arg2, 0, 0);
86 void
87 message5 (char const *format_msgid, char const *arg1, char const *arg2,
88 char const *arg3, char const *arg4)
90 if (paginate)
92 char *p;
93 char const *arg[5];
94 int i;
95 size_t size[5];
96 size_t total_size = offsetof (struct msg, args);
97 struct msg *new;
99 arg[0] = format_msgid;
100 arg[1] = arg1;
101 arg[2] = arg2;
102 arg[3] = arg3 ? arg3 : "";
103 arg[4] = arg4 ? arg4 : "";
105 for (i = 0; i < 5; i++)
106 total_size += size[i] = strlen (arg[i]) + 1;
108 new = xmalloc (total_size);
110 for (i = 0, p = new->args; i < 5; p += size[i++])
111 memcpy (p, arg[i], size[i]);
113 *msg_chain_end = new;
114 new->next = 0;
115 msg_chain_end = &new->next;
117 else
119 if (sdiff_merge_assist)
120 putchar (' ');
121 printf (_(format_msgid), arg1, arg2, arg3, arg4);
125 /* Output all the messages that were saved up by calls to 'message'. */
127 void
128 print_message_queue (void)
130 char const *arg[5];
131 int i;
132 struct msg *m = msg_chain;
134 while (m)
136 struct msg *next = m->next;
137 arg[0] = m->args;
138 for (i = 0; i < 4; i++)
139 arg[i + 1] = arg[i] + strlen (arg[i]) + 1;
140 printf (_(arg[0]), arg[1], arg[2], arg[3], arg[4]);
141 free (m);
142 m = next;
146 /* Call before outputting the results of comparing files NAME0 and NAME1
147 to set up OUTFILE, the stdio stream for the output to go to.
149 Usually, OUTFILE is just stdout. But when -l was specified
150 we fork off a 'pr' and make OUTFILE a pipe to it.
151 'pr' then outputs to our stdout. */
153 static char const *current_name0;
154 static char const *current_name1;
155 static bool currently_recursive;
157 void
158 setup_output (char const *name0, char const *name1, bool recursive)
160 current_name0 = name0;
161 current_name1 = name1;
162 currently_recursive = recursive;
163 outfile = 0;
166 #if HAVE_WORKING_FORK
167 static pid_t pr_pid;
168 #endif
170 static char c_escape_char (char c)
172 switch (c) {
173 case '\a': return 'a';
174 case '\b': return 'b';
175 case '\t': return 't';
176 case '\n': return 'n';
177 case '\v': return 'v';
178 case '\f': return 'f';
179 case '\r': return 'r';
180 case '"': return '"';
181 case '\\': return '\\';
182 default:
183 return c < 32;
187 static char *
188 c_escape (char const *str)
190 char const *s;
191 size_t plus = 0;
192 bool must_quote = false;
194 for (s = str; *s; s++)
196 char c = *s;
198 if (c == ' ')
200 must_quote = true;
201 continue;
203 switch (c_escape_char (*s))
205 case 1:
206 plus += 3;
207 /* fall through */
208 case 0:
209 break;
210 default:
211 plus++;
212 break;
216 if (must_quote || plus)
218 size_t s_len = s - str;
219 char *buffer = xmalloc (s_len + plus + 3);
220 char *b = buffer;
222 *b++ = '"';
223 for (s = str; *s; s++)
225 char c = *s;
226 char escape = c_escape_char (c);
228 switch (escape)
230 case 0:
231 *b++ = c;
232 break;
233 case 1:
234 *b++ = '\\';
235 *b++ = ((c >> 6) & 03) + '0';
236 *b++ = ((c >> 3) & 07) + '0';
237 *b++ = ((c >> 0) & 07) + '0';
238 break;
239 default:
240 *b++ = '\\';
241 *b++ = escape;
242 break;
245 *b++ = '"';
246 *b = 0;
247 return buffer;
250 return (char *) str;
253 void
254 begin_output (void)
256 char *names[2];
257 char *name;
259 if (outfile != 0)
260 return;
262 names[0] = c_escape (current_name0);
263 names[1] = c_escape (current_name1);
265 /* Construct the header of this piece of diff. */
266 /* POSIX 1003.1-2001 specifies this format. But there are some bugs in
267 the standard: it says that we must print only the last component
268 of the pathnames, and it requires two spaces after "diff" if
269 there are no options. These requirements are silly and do not
270 match historical practice. */
271 name = xasprintf ("diff%s %s %s", switch_string, names[0], names[1]);
273 if (paginate)
275 char const *argv[4];
277 if (fflush (stdout) != 0)
278 pfatal_with_name (_("write failed"));
280 argv[0] = pr_program;
281 argv[1] = "-h";
282 argv[2] = name;
283 argv[3] = 0;
285 /* Make OUTFILE a pipe to a subsidiary 'pr'. */
287 #if HAVE_WORKING_FORK
288 int pipes[2];
290 if (pipe (pipes) != 0)
291 pfatal_with_name ("pipe");
293 pr_pid = fork ();
294 if (pr_pid < 0)
295 pfatal_with_name ("fork");
297 if (pr_pid == 0)
299 close (pipes[1]);
300 if (pipes[0] != STDIN_FILENO)
302 if (dup2 (pipes[0], STDIN_FILENO) < 0)
303 pfatal_with_name ("dup2");
304 close (pipes[0]);
307 execv (pr_program, (char **) argv);
308 _exit (errno == ENOENT ? 127 : 126);
310 else
312 close (pipes[0]);
313 outfile = fdopen (pipes[1], "w");
314 if (!outfile)
315 pfatal_with_name ("fdopen");
317 #else
318 char *command = system_quote_argv (SCI_SYSTEM, (char **) argv);
319 errno = 0;
320 outfile = popen (command, "w");
321 if (!outfile)
322 pfatal_with_name (command);
323 free (command);
324 #endif
327 else
330 /* If -l was not specified, output the diff straight to 'stdout'. */
332 outfile = stdout;
334 /* If handling multiple files (because scanning a directory),
335 print which files the following output is about. */
336 if (currently_recursive)
337 printf ("%s\n", name);
340 free (name);
342 /* A special header is needed at the beginning of context output. */
343 switch (output_style)
345 case OUTPUT_CONTEXT:
346 print_context_header (files, (char const *const *)names, false);
347 break;
349 case OUTPUT_UNIFIED:
350 print_context_header (files, (char const *const *)names, true);
351 break;
353 default:
354 break;
357 if (names[0] != current_name0)
358 free (names[0]);
359 if (names[1] != current_name1)
360 free (names[1]);
363 /* Call after the end of output of diffs for one file.
364 Close OUTFILE and get rid of the 'pr' subfork. */
366 void
367 finish_output (void)
369 if (outfile != 0 && outfile != stdout)
371 int status;
372 int wstatus;
373 int werrno = 0;
374 if (ferror (outfile))
375 fatal ("write failed");
376 #if ! HAVE_WORKING_FORK
377 wstatus = pclose (outfile);
378 if (wstatus == -1)
379 werrno = errno;
380 #else
381 if (fclose (outfile) != 0)
382 pfatal_with_name (_("write failed"));
383 if (waitpid (pr_pid, &wstatus, 0) < 0)
384 pfatal_with_name ("waitpid");
385 #endif
386 status = (! werrno && WIFEXITED (wstatus)
387 ? WEXITSTATUS (wstatus)
388 : INT_MAX);
389 if (status)
390 error (EXIT_TROUBLE, werrno,
391 _(status == 126
392 ? "subsidiary program '%s' could not be invoked"
393 : status == 127
394 ? "subsidiary program '%s' not found"
395 : status == INT_MAX
396 ? "subsidiary program '%s' failed"
397 : "subsidiary program '%s' failed (exit status %d)"),
398 pr_program, status);
401 outfile = 0;
404 /* Compare two lines (typically one from each input file)
405 according to the command line options.
406 For efficiency, this is invoked only when the lines do not match exactly
407 but an option like -i might cause us to ignore the difference.
408 Return nonzero if the lines differ. */
410 bool
411 lines_differ (char const *s1, char const *s2)
413 register char const *t1 = s1;
414 register char const *t2 = s2;
415 size_t column = 0;
417 while (1)
419 register unsigned char c1 = *t1++;
420 register unsigned char c2 = *t2++;
422 /* Test for exact char equality first, since it's a common case. */
423 if (c1 != c2)
425 switch (ignore_white_space)
427 case IGNORE_ALL_SPACE:
428 /* For -w, just skip past any white space. */
429 while (isspace (c1) && c1 != '\n') c1 = *t1++;
430 while (isspace (c2) && c2 != '\n') c2 = *t2++;
431 break;
433 case IGNORE_SPACE_CHANGE:
434 /* For -b, advance past any sequence of white space in
435 line 1 and consider it just one space, or nothing at
436 all if it is at the end of the line. */
437 if (isspace (c1))
439 while (c1 != '\n')
441 c1 = *t1++;
442 if (! isspace (c1))
444 --t1;
445 c1 = ' ';
446 break;
451 /* Likewise for line 2. */
452 if (isspace (c2))
454 while (c2 != '\n')
456 c2 = *t2++;
457 if (! isspace (c2))
459 --t2;
460 c2 = ' ';
461 break;
466 if (c1 != c2)
468 /* If we went too far when doing the simple test
469 for equality, go back to the first non-white-space
470 character in both sides and try again. */
471 if (c2 == ' ' && c1 != '\n'
472 && s1 + 1 < t1
473 && isspace ((unsigned char) t1[-2]))
475 --t1;
476 continue;
478 if (c1 == ' ' && c2 != '\n'
479 && s2 + 1 < t2
480 && isspace ((unsigned char) t2[-2]))
482 --t2;
483 continue;
487 break;
489 case IGNORE_TRAILING_SPACE:
490 case IGNORE_TAB_EXPANSION_AND_TRAILING_SPACE:
491 if (isspace (c1) && isspace (c2))
493 unsigned char c;
494 if (c1 != '\n')
496 char const *p = t1;
497 while ((c = *p) != '\n' && isspace (c))
498 ++p;
499 if (c != '\n')
500 break;
502 if (c2 != '\n')
504 char const *p = t2;
505 while ((c = *p) != '\n' && isspace (c))
506 ++p;
507 if (c != '\n')
508 break;
510 /* Both lines have nothing but whitespace left. */
511 return false;
513 if (ignore_white_space == IGNORE_TRAILING_SPACE)
514 break;
515 /* Fall through. */
516 case IGNORE_TAB_EXPANSION:
517 if ((c1 == ' ' && c2 == '\t')
518 || (c1 == '\t' && c2 == ' '))
520 size_t column2 = column;
521 for (;; c1 = *t1++)
523 if (c1 == ' ')
524 column++;
525 else if (c1 == '\t')
526 column += tabsize - column % tabsize;
527 else
528 break;
530 for (;; c2 = *t2++)
532 if (c2 == ' ')
533 column2++;
534 else if (c2 == '\t')
535 column2 += tabsize - column2 % tabsize;
536 else
537 break;
539 if (column != column2)
540 return true;
542 break;
544 case IGNORE_NO_WHITE_SPACE:
545 break;
548 /* Lowercase all letters if -i is specified. */
550 if (ignore_case)
552 c1 = tolower (c1);
553 c2 = tolower (c2);
556 if (c1 != c2)
557 break;
559 if (c1 == '\n')
560 return false;
562 column += c1 == '\t' ? tabsize - column % tabsize : 1;
565 return true;
568 /* Find the consecutive changes at the start of the script START.
569 Return the last link before the first gap. */
571 struct change * _GL_ATTRIBUTE_CONST
572 find_change (struct change *start)
574 return start;
577 struct change * _GL_ATTRIBUTE_CONST
578 find_reverse_change (struct change *start)
580 return start;
583 /* Divide SCRIPT into pieces by calling HUNKFUN and
584 print each piece with PRINTFUN.
585 Both functions take one arg, an edit script.
587 HUNKFUN is called with the tail of the script
588 and returns the last link that belongs together with the start
589 of the tail.
591 PRINTFUN takes a subscript which belongs together (with a null
592 link at the end) and prints it. */
594 void
595 print_script (struct change *script,
596 struct change * (*hunkfun) (struct change *),
597 void (*printfun) (struct change *))
599 struct change *next = script;
601 while (next)
603 struct change *this, *end;
605 /* Find a set of changes that belong together. */
606 this = next;
607 end = (*hunkfun) (next);
609 /* Disconnect them from the rest of the changes,
610 making them a hunk, and remember the rest for next iteration. */
611 next = end->link;
612 end->link = 0;
613 #ifdef DEBUG
614 debug_script (this);
615 #endif
617 /* Print this hunk. */
618 (*printfun) (this);
620 /* Reconnect the script so it will all be freed properly. */
621 end->link = next;
625 /* Print the text of a single line LINE,
626 flagging it with the characters in LINE_FLAG (which say whether
627 the line is inserted, deleted, changed, etc.). LINE_FLAG must not
628 end in a blank, unless it is a single blank. */
630 void
631 print_1_line (char const *line_flag, char const *const *line)
633 char const *base = line[0], *limit = line[1]; /* Help the compiler. */
634 FILE *out = outfile; /* Help the compiler some more. */
635 char const *flag_format = 0;
637 /* If -T was specified, use a Tab between the line-flag and the text.
638 Otherwise use a Space (as Unix diff does).
639 Print neither space nor tab if line-flags are empty.
640 But omit trailing blanks if requested. */
642 if (line_flag && *line_flag)
644 char const *flag_format_1 = flag_format = initial_tab ? "%s\t" : "%s ";
645 char const *line_flag_1 = line_flag;
647 if (suppress_blank_empty && **line == '\n')
649 flag_format_1 = "%s";
651 /* This hack to omit trailing blanks takes advantage of the
652 fact that the only way that LINE_FLAG can end in a blank
653 is when LINE_FLAG consists of a single blank. */
654 line_flag_1 += *line_flag_1 == ' ';
657 fprintf (out, flag_format_1, line_flag_1);
660 output_1_line (base, limit, flag_format, line_flag);
662 if ((!line_flag || line_flag[0]) && limit[-1] != '\n')
663 fprintf (out, "\n\\ %s\n", _("No newline at end of file"));
666 /* Output a line from BASE up to LIMIT.
667 With -t, expand white space characters to spaces, and if FLAG_FORMAT
668 is nonzero, output it with argument LINE_FLAG after every
669 internal carriage return, so that tab stops continue to line up. */
671 void
672 output_1_line (char const *base, char const *limit, char const *flag_format,
673 char const *line_flag)
675 if (!expand_tabs)
676 fwrite (base, sizeof (char), limit - base, outfile);
677 else
679 register FILE *out = outfile;
680 register unsigned char c;
681 register char const *t = base;
682 register size_t column = 0;
683 size_t tab_size = tabsize;
685 while (t < limit)
686 switch ((c = *t++))
688 case '\t':
690 size_t spaces = tab_size - column % tab_size;
691 column += spaces;
693 putc (' ', out);
694 while (--spaces);
696 break;
698 case '\r':
699 putc (c, out);
700 if (flag_format && t < limit && *t != '\n')
701 fprintf (out, flag_format, line_flag);
702 column = 0;
703 break;
705 case '\b':
706 if (column == 0)
707 continue;
708 column--;
709 putc (c, out);
710 break;
712 default:
713 column += isprint (c) != 0;
714 putc (c, out);
715 break;
720 char const change_letter[] = { 0, 'd', 'a', 'c' };
722 /* Translate an internal line number (an index into diff's table of lines)
723 into an actual line number in the input file.
724 The internal line number is I. FILE points to the data on the file.
726 Internal line numbers count from 0 starting after the prefix.
727 Actual line numbers count from 1 within the entire file. */
729 lin _GL_ATTRIBUTE_PURE
730 translate_line_number (struct file_data const *file, lin i)
732 return i + file->prefix_lines + 1;
735 /* Translate a line number range. This is always done for printing,
736 so for convenience translate to long int rather than lin, so that the
737 caller can use printf with "%ld" without casting. */
739 void
740 translate_range (struct file_data const *file,
741 lin a, lin b,
742 long int *aptr, long int *bptr)
744 *aptr = translate_line_number (file, a - 1) + 1;
745 *bptr = translate_line_number (file, b + 1) - 1;
748 /* Print a pair of line numbers with SEPCHAR, translated for file FILE.
749 If the two numbers are identical, print just one number.
751 Args A and B are internal line numbers.
752 We print the translated (real) line numbers. */
754 void
755 print_number_range (char sepchar, struct file_data *file, lin a, lin b)
757 long int trans_a, trans_b;
758 translate_range (file, a, b, &trans_a, &trans_b);
760 /* Note: we can have B < A in the case of a range of no lines.
761 In this case, we should print the line number before the range,
762 which is B. */
763 if (trans_b > trans_a)
764 fprintf (outfile, "%ld%c%ld", trans_a, sepchar, trans_b);
765 else
766 fprintf (outfile, "%ld", trans_b);
769 /* Look at a hunk of edit script and report the range of lines in each file
770 that it applies to. HUNK is the start of the hunk, which is a chain
771 of 'struct change'. The first and last line numbers of file 0 are stored in
772 *FIRST0 and *LAST0, and likewise for file 1 in *FIRST1 and *LAST1.
773 Note that these are internal line numbers that count from 0.
775 If no lines from file 0 are deleted, then FIRST0 is LAST0+1.
777 Return UNCHANGED if only ignorable lines are inserted or deleted,
778 OLD if lines of file 0 are deleted,
779 NEW if lines of file 1 are inserted,
780 and CHANGED if both kinds of changes are found. */
782 enum changes
783 analyze_hunk (struct change *hunk,
784 lin *first0, lin *last0,
785 lin *first1, lin *last1)
787 struct change *next;
788 lin l0, l1;
789 lin show_from, show_to;
790 lin i;
791 bool trivial = ignore_blank_lines || ignore_regexp.fastmap;
792 size_t trivial_length = ignore_blank_lines - 1;
793 /* If 0, ignore zero-length lines;
794 if SIZE_MAX, do not ignore lines just because of their length. */
796 bool skip_white_space =
797 ignore_blank_lines && IGNORE_TRAILING_SPACE <= ignore_white_space;
798 bool skip_leading_white_space =
799 skip_white_space && IGNORE_SPACE_CHANGE <= ignore_white_space;
801 char const * const *linbuf0 = files[0].linbuf; /* Help the compiler. */
802 char const * const *linbuf1 = files[1].linbuf;
804 show_from = show_to = 0;
806 *first0 = hunk->line0;
807 *first1 = hunk->line1;
809 next = hunk;
812 l0 = next->line0 + next->deleted - 1;
813 l1 = next->line1 + next->inserted - 1;
814 show_from += next->deleted;
815 show_to += next->inserted;
817 for (i = next->line0; i <= l0 && trivial; i++)
819 char const *line = linbuf0[i];
820 char const *newline = linbuf0[i + 1] - 1;
821 size_t len = newline - line;
822 char const *p = line;
823 if (skip_white_space)
824 for (; *p != '\n'; p++)
825 if (! isspace ((unsigned char) *p))
827 if (! skip_leading_white_space)
828 p = line;
829 break;
831 if (newline - p != trivial_length
832 && (! ignore_regexp.fastmap
833 || re_search (&ignore_regexp, line, len, 0, len, 0) < 0))
834 trivial = 0;
837 for (i = next->line1; i <= l1 && trivial; i++)
839 char const *line = linbuf1[i];
840 char const *newline = linbuf1[i + 1] - 1;
841 size_t len = newline - line;
842 char const *p = line;
843 if (skip_white_space)
844 for (; *p != '\n'; p++)
845 if (! isspace ((unsigned char) *p))
847 if (! skip_leading_white_space)
848 p = line;
849 break;
851 if (newline - p != trivial_length
852 && (! ignore_regexp.fastmap
853 || re_search (&ignore_regexp, line, len, 0, len, 0) < 0))
854 trivial = 0;
857 while ((next = next->link) != 0);
859 *last0 = l0;
860 *last1 = l1;
862 /* If all inserted or deleted lines are ignorable,
863 tell the caller to ignore this hunk. */
865 if (trivial)
866 return UNCHANGED;
868 return (show_from ? OLD : UNCHANGED) | (show_to ? NEW : UNCHANGED);
871 /* Concatenate three strings, returning a newly malloc'd string. */
873 char *
874 concat (char const *s1, char const *s2, char const *s3)
876 char *new = xmalloc (strlen (s1) + strlen (s2) + strlen (s3) + 1);
877 sprintf (new, "%s%s%s", s1, s2, s3);
878 return new;
881 /* Yield a new block of SIZE bytes, initialized to zero. */
883 void *
884 zalloc (size_t size)
886 void *p = xmalloc (size);
887 memset (p, 0, size);
888 return p;
891 void
892 debug_script (struct change *sp)
894 fflush (stdout);
896 for (; sp; sp = sp->link)
898 long int line0 = sp->line0;
899 long int line1 = sp->line1;
900 long int deleted = sp->deleted;
901 long int inserted = sp->inserted;
902 fprintf (stderr, "%3ld %3ld delete %ld insert %ld\n",
903 line0, line1, deleted, inserted);
906 fflush (stderr);