1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
|
Upstream-Status="Inappropriate [debian patch]"
Index: patch-2.6.1/patch.man
===================================================================
--- patch-2.6.1.orig/patch.man
+++ patch-2.6.1/patch.man
@@ -557,6 +557,15 @@ instead of the default
.B \&.rej
file. When \fIrejectfile\fP is \fB\-\fP, discard rejects.
.TP
+.BI \*=global\-reject\-file= rejectfile
+Put all rejects into
+.I rejectfile
+instead of creating separate reject files for all files that have rejects. The
+.I rejectfile
+will contain headers that identify which file each reject refers to. Note that
+the global reject file is created even if \-\-dry\-run is specified (while
+non-global reject files will only be created without \-\-dry\-run).
+.TP
\fB\-R\fP or \fB\*=reverse\fP
Assume that this patch was created with the old and new files swapped.
(Yes, I'm afraid that does happen occasionally, human nature being what it
Index: patch-2.6.1/src/patch.c
===================================================================
--- patch-2.6.1.orig/src/patch.c
+++ patch-2.6.1/src/patch.c
@@ -52,6 +52,7 @@ static void reinitialize_almost_everythi
static void remove_if_needed (char const *, int volatile *);
static void usage (FILE *, int) __attribute__((noreturn));
+static void reject_header (const char *filename);
static void abort_hunk (bool, bool);
static void abort_hunk_context (bool, bool);
static void abort_hunk_unified (bool, bool);
@@ -83,6 +84,7 @@ static int Argc;
static char * const *Argv;
static FILE *rejfp; /* reject file pointer */
+static char *global_reject;
static char const *patchname;
static char *rejname;
@@ -159,6 +161,10 @@ main (int argc, char **argv)
/* Make sure we clean up in case of disaster. */
set_signals (false);
+ /* initialize global reject file */
+ if (global_reject)
+ init_reject ();
+
if (inname && outfile)
{
apply_empty_patch = true;
@@ -205,8 +211,9 @@ main (int argc, char **argv)
init_output (TMPOUTNAME, exclusive, &outstate);
}
- /* initialize reject file */
- init_reject ();
+ /* initialize per-patch reject file */
+ if (!global_reject)
+ init_reject ();
/* find out where all the lines are */
if (!skip_rest_of_patch)
@@ -295,6 +302,8 @@ main (int argc, char **argv)
|| ! where
|| ! apply_hunk (&outstate, where))))
{
+ if (!failed)
+ reject_header(outname);
abort_hunk (! failed, reverse);
failed++;
if (verbosity == VERBOSE ||
@@ -331,7 +340,8 @@ main (int argc, char **argv)
fclose (outstate.ofp);
outstate.ofp = 0;
}
- fclose (rejfp);
+ if (!global_reject)
+ fclose (rejfp);
continue;
}
@@ -430,13 +440,13 @@ main (int argc, char **argv)
struct stat rejst;
if ((failed && fstat (fileno (rejfp), &rejst) != 0)
- || fclose (rejfp) != 0)
+ || (( !global_reject && fclose (rejfp) != 0)))
write_fatal ();
if (failed) {
somefailed = true;
say ("%d out of %d hunk%s %s", failed, hunk, "s" + (hunk == 1),
skip_rest_of_patch ? "ignored" : "FAILED");
- if (outname && (! rejname || strcmp (rejname, "-") != 0)) {
+ if (!global_reject && outname && (! rejname || strcmp (rejname, "-") != 0)) {
char *rej = rejname;
if (!rejname) {
/* FIXME: This should really be done differnely! */
@@ -485,6 +495,23 @@ main (int argc, char **argv)
}
set_signals (true);
}
+ if (global_reject)
+ {
+ struct stat rejst;
+
+ if ((somefailed && fstat (fileno (rejfp), &rejst) != 0)
+ || fclose (rejfp) != 0)
+ write_fatal ();
+ if (somefailed)
+ {
+ say (" -- saving rejects to file %s\n", quotearg (global_reject));
+ /*if (! dry_run)
+ {*/
+ move_file (TMPREJNAME, &TMPREJNAME_needs_removal,
+ &rejst, global_reject, 0644, false);
+ /*}*/
+ }
+ }
if (outstate.ofp && (ferror (outstate.ofp) || fclose (outstate.ofp) != 0))
write_fatal ();
cleanup ();
@@ -572,6 +599,7 @@ static struct option const longopts[] =
{"posix", no_argument, NULL, CHAR_MAX + 7},
{"quoting-style", required_argument, NULL, CHAR_MAX + 8},
{"reject-format", required_argument, NULL, CHAR_MAX + 9},
+ {"global-reject-file", required_argument, NULL, CHAR_MAX + 10},
{NULL, no_argument, NULL, 0}
};
@@ -636,6 +664,7 @@ static char const *const option_help[] =
"",
" -d DIR --directory=DIR Change the working directory to DIR first.",
" --reject-format=FORMAT Create 'context' or 'unified' rejects.",
+" --global-reject-file=file Put all rejects into one file.",
" --binary Read and write data in binary mode.",
"",
" -v --version Output version info.",
@@ -852,6 +881,9 @@ get_some_switches (void)
else
usage (stderr, 2);
break;
+ case CHAR_MAX + 10:
+ global_reject = savestr (optarg);
+ break;
default:
usage (stderr, 2);
}
@@ -1512,6 +1544,37 @@ similar (register char const *a, registe
}
}
+ static char *
+format_timestamp (char timebuf[37], bool which)
+{
+ time_t ts = pch_timestamp(which);
+ if (ts != -1)
+ {
+ struct tm *tm = localtime(&ts);
+ strftime(timebuf, 37, "\t%Y-%m-%d %H:%M:%S.000000000 %z", tm);
+ }
+ else
+ timebuf[0] = 0;
+ return timebuf;
+}
+
+/* Write a header in a reject file that combines multiple hunks. */
+static void
+reject_header (const char *outname)
+{
+ char timebuf0[37], timebuf1[37];
+ if (!global_reject)
+ return;
+ if (diff_type == UNI_DIFF)
+ fprintf(rejfp, "--- %s.orig%s\n+++ %s%s\n",
+ outname, format_timestamp(timebuf0, reverse),
+ outname, format_timestamp(timebuf1, !reverse));
+ else
+ fprintf(rejfp, "*** %s.orig%s\n--- %s%s\n",
+ outname, format_timestamp(timebuf0, reverse),
+ outname, format_timestamp(timebuf1, !reverse));
+}
+
/* Make a temporary file. */
#if HAVE_MKTEMP && ! HAVE_DECL_MKTEMP && ! defined mktemp
|