5
#include "revision.h"
6
#include "tag.h"
7
#include "string-list.h"
8
+#include "gpg-interface.h"
9
10
static const char * const fmt_merge_msg_usage[] = {
11
"git fmt-merge-msg [-m <message>] [--log[=<n>]|--no-log] [--file <file>]",
263
strbuf_addf(out, " into %s\n", current_branch);
264
}
265
266
+static void fmt_tag_signature(struct strbuf *tagbuf,
267
+ struct strbuf *sig,
268
+ const char *buf,
269
+ unsigned long len)
270
+{
271
+ const char *tag_body = strstr(buf, "\n\n");
272
+ if (tag_body) {
273
+ tag_body += 2;
274
+ strbuf_add(tagbuf, tag_body, buf + len - tag_body);
275
+ }
276
+ strbuf_complete_line(tagbuf);
277
+ strbuf_add_lines(tagbuf, "# ", sig->buf, sig->len);
278
+}
279
+
280
+static void fmt_merge_msg_sigs(struct strbuf *out)
281
+{
282
+ int i, tag_number = 0, first_tag = 0;
283
+ struct strbuf tagbuf = STRBUF_INIT;
284
+
285
+ for (i = 0; i < origins.nr; i++) {
286
+ unsigned char *sha1 = origins.items[i].util;
287
+ enum object_type type;
288
+ unsigned long size, len;
289
+ char *buf = read_sha1_file(sha1, &type, &size);
290
+ struct strbuf sig = STRBUF_INIT;
291
+
292
+ if (!buf || type != OBJ_TAG)
293
+ goto next;
294
+ len = parse_signature(buf, size);
295
+
296
+ if (size == len)
297
+ ; /* merely annotated */
298
+ else if (verify_signed_buffer(buf, len, buf + len, size - len, &sig)) {
299
+ if (!sig.len)
300
+ strbuf_addstr(&sig, "gpg verification failed.\n");
301
+ }
302
+
303
+ if (!tag_number++) {
304
+ fmt_tag_signature(&tagbuf, &sig, buf, len);
305
+ first_tag = i;
306
+ } else {
307
+ if (tag_number == 2) {
308
+ struct strbuf tagline = STRBUF_INIT;
309
+ strbuf_addf(&tagline, "\n# %s\n",
310
+ origins.items[first_tag].string);
311
+ strbuf_insert(&tagbuf, 0, tagline.buf,
312
+ tagline.len);
313
+ strbuf_release(&tagline);
314
+ }
315
+ strbuf_addf(&tagbuf, "\n# %s\n",
316
+ origins.items[i].string);
317
+ fmt_tag_signature(&tagbuf, &sig, buf, len);
318
+ }
319
+ strbuf_release(&sig);
320
+ next:
321
+ free(buf);
322
+ }
323
+ if (tagbuf.len) {
324
+ strbuf_addch(out, '\n');
325
+ strbuf_addbuf(out, &tagbuf);
326
+ }
327
+ strbuf_release(&tagbuf);
328
+}
329
+
330
int fmt_merge_msg(struct strbuf *in, struct strbuf *out,
331
struct fmt_merge_msg_opts *opts)
332
{
358
if (opts->add_title && srcs.nr)
359
fmt_merge_msg_title(out, current_branch);
360
361
+ if (origins.nr)
362
+ fmt_merge_msg_sigs(out);
363
+
364
if (opts->shortlog_len) {
365
struct commit *head;
366
struct rev_info rev;
378
shortlog(origins.items[i].string, origins.items[i].util,
379
head, &rev, opts->shortlog_len, out);
380
}
313
- if (out->len && out->buf[out->len-1] != '\n')
314
- strbuf_addch(out, '\n');
381
+
382
+ strbuf_complete_line(out);
383
return 0;
384
}
385