X-Git-Url: https://git.octo.it/?a=blobdiff_plain;f=apply.c;h=590adc6afafa98e389dcafc2f8c432db09412d4e;hb=313c4714c5ec1673805b952ba79d910a42e8937c;hp=3e53b3438169bcaaf4db97669b062ebe14335fe6;hpb=7d8b7c21c9c0bee0d94fcf3b350e24ebdb920b74;p=git.git diff --git a/apply.c b/apply.c index 3e53b343..590adc6a 100644 --- a/apply.c +++ b/apply.c @@ -23,10 +23,11 @@ static int numstat = 0; static int summary = 0; static int check = 0; static int apply = 1; +static int no_add = 0; static int show_index_info = 0; static int line_termination = '\n'; static const char apply_usage[] = -"git-apply [--stat] [--numstat] [--summary] [--check] [--index] [--apply] [--index-info] [-z] ..."; +"git-apply [--stat] [--numstat] [--summary] [--check] [--index] [--apply] [--no-add] [--index-info] [-z] ..."; /* * For "diff-stat" like behaviour, we keep track of the biggest change @@ -53,7 +54,7 @@ struct fragment { struct patch { char *new_name, *old_name, *def_name; unsigned int old_mode, new_mode; - int is_rename, is_copy, is_new, is_delete; + int is_rename, is_copy, is_new, is_delete, is_binary; int lines_added, lines_deleted; int score; struct fragment *fragments; @@ -369,7 +370,7 @@ static int gitdiff_index(const char *line, struct patch *patch) int len; ptr = strchr(line, '.'); - if (!ptr || ptr[1] != '.' || 40 <= ptr - line) + if (!ptr || ptr[1] != '.' || 40 < ptr - line) return 0; len = ptr - line; memcpy(patch->old_sha1_prefix, line, len); @@ -383,7 +384,7 @@ static int gitdiff_index(const char *line, struct patch *patch) ptr = eol; len = ptr - line; - if (40 <= len) + if (40 < len) return 0; memcpy(patch->new_sha1_prefix, line, len); patch->new_sha1_prefix[len] = 0; @@ -890,8 +891,19 @@ static int parse_chunk(char *buffer, unsigned long size, struct patch *patch) patchsize = parse_single_patch(buffer + offset + hdrsize, size - offset - hdrsize, patch); - if (!patchsize && !metadata_changes(patch)) - die("patch with only garbage at line %d", linenr); + if (!patchsize && !metadata_changes(patch)) { + static const char binhdr[] = "Binary files "; + + if (sizeof(binhdr) - 1 < size - offset - hdrsize && + !memcmp(binhdr, buffer + hdrsize + offset, + sizeof(binhdr)-1)) + patch->is_binary = 1; + + if (patch->is_binary && !apply && !check) + ; + else + die("patch with only garbage at line %d", linenr); + } return offset + hdrsize + patchsize; } @@ -949,9 +961,12 @@ static void show_stats(struct patch *patch) add = (add * max + max_change / 2) / max_change; del = total - add; } - printf(" %s%-*s |%5d %.*s%.*s\n", prefix, - len, name, patch->lines_added + patch->lines_deleted, - add, pluses, del, minuses); + if (patch->is_binary) + printf(" %s%-*s | Bin\n", prefix, len, name); + else + printf(" %s%-*s |%5d %.*s%.*s\n", prefix, + len, name, patch->lines_added + patch->lines_deleted, + add, pluses, del, minuses); if (qname) free(qname); } @@ -1099,8 +1114,10 @@ static int apply_one_fragment(struct buffer_desc *desc, struct fragment *frag) break; /* Fall-through for ' ' */ case '+': - memcpy(new + newsize, patch + 1, plen); - newsize += plen; + if (*patch != '+' || !no_add) { + memcpy(new + newsize, patch + 1, plen); + newsize += plen; + } break; case '@': case '\\': /* Ignore it, we already handled it */ @@ -1697,6 +1714,10 @@ int main(int argc, char **argv) excludes = x; continue; } + if (!strcmp(arg, "--no-add")) { + no_add = 1; + continue; + } if (!strcmp(arg, "--stat")) { apply = 0; diffstat = 1;