summaryrefslogtreecommitdiff
path: root/diff.c
diff options
context:
space:
mode:
Diffstat (limited to 'diff.c')
-rw-r--r--diff.c229
1 files changed, 129 insertions, 100 deletions
diff --git a/diff.c b/diff.c
index 46260ed7a1..cc8e81290a 100644
--- a/diff.c
+++ b/diff.c
@@ -13,7 +13,6 @@
#include "run-command.h"
#include "utf8.h"
#include "userdiff.h"
-#include "sigchain.h"
#include "submodule-config.h"
#include "submodule.h"
#include "ll-merge.h"
@@ -27,6 +26,7 @@
#endif
static int diff_detect_rename_default;
+static int diff_compaction_heuristic; /* experimental */
static int diff_rename_limit_default = 400;
static int diff_suppress_blank_empty;
static int diff_use_color_default = -1;
@@ -169,6 +169,11 @@ long parse_algorithm_value(const char *value)
* never be affected by the setting of diff.renames
* the user happens to have in the configuration file.
*/
+void init_diff_ui_defaults(void)
+{
+ diff_detect_rename_default = 1;
+}
+
int git_diff_ui_config(const char *var, const char *value, void *cb)
{
if (!strcmp(var, "diff.color") || !strcmp(var, "color.diff")) {
@@ -185,6 +190,10 @@ int git_diff_ui_config(const char *var, const char *value, void *cb)
diff_detect_rename_default = git_config_rename(var, value);
return 0;
}
+ if (!strcmp(var, "diff.compactionheuristic")) {
+ diff_compaction_heuristic = git_config_bool(var, value);
+ return 0;
+ }
if (!strcmp(var, "diff.autorefreshindex")) {
diff_auto_refresh_index = git_config_bool(var, value);
return 0;
@@ -322,7 +331,7 @@ static struct diff_tempfile {
*/
const char *name;
- char hex[41];
+ char hex[GIT_SHA1_HEXSZ + 1];
char mode[10];
/*
@@ -345,7 +354,6 @@ struct emit_callback {
const char **label_path;
struct diff_words_data *diff_words;
struct diff_options *opt;
- int *found_changesp;
struct strbuf *header;
};
@@ -713,7 +721,6 @@ static void emit_rewrite_diff(const char *name_a,
memset(&ecbdata, 0, sizeof(ecbdata));
ecbdata.color_diff = want_color(o->use_color);
- ecbdata.found_changesp = &o->found_changes;
ecbdata.ws_rule = whitespace_rule(name_b);
ecbdata.opt = o;
if (ecbdata.ws_rule & WS_BLANK_AT_EOF) {
@@ -1207,12 +1214,13 @@ static void fn_out_consume(void *priv, char *line, unsigned long len)
struct diff_options *o = ecbdata->opt;
const char *line_prefix = diff_line_prefix(o);
+ o->found_changes = 1;
+
if (ecbdata->header) {
- fprintf(ecbdata->opt->file, "%s", ecbdata->header->buf);
+ fprintf(o->file, "%s", ecbdata->header->buf);
strbuf_reset(ecbdata->header);
ecbdata->header = NULL;
}
- *(ecbdata->found_changesp) = 1;
if (ecbdata->label_path[0]) {
const char *name_a_tab, *name_b_tab;
@@ -1220,9 +1228,9 @@ static void fn_out_consume(void *priv, char *line, unsigned long len)
name_a_tab = strchr(ecbdata->label_path[0], ' ') ? "\t" : "";
name_b_tab = strchr(ecbdata->label_path[1], ' ') ? "\t" : "";
- fprintf(ecbdata->opt->file, "%s%s--- %s%s%s\n",
+ fprintf(o->file, "%s%s--- %s%s%s\n",
line_prefix, meta, ecbdata->label_path[0], reset, name_a_tab);
- fprintf(ecbdata->opt->file, "%s%s+++ %s%s%s\n",
+ fprintf(o->file, "%s%s+++ %s%s%s\n",
line_prefix, meta, ecbdata->label_path[1], reset, name_b_tab);
ecbdata->label_path[0] = ecbdata->label_path[1] = NULL;
}
@@ -1240,15 +1248,7 @@ static void fn_out_consume(void *priv, char *line, unsigned long len)
find_lno(line, ecbdata);
emit_hunk_header(ecbdata, line, len);
if (line[len-1] != '\n')
- putc('\n', ecbdata->opt->file);
- return;
- }
-
- if (len < 1) {
- emit_line(ecbdata->opt, reset, reset, line, len);
- if (ecbdata->diff_words
- && ecbdata->diff_words->type == DIFF_WORDS_PORCELAIN)
- fputs("~\n", ecbdata->opt->file);
+ putc('\n', o->file);
return;
}
@@ -1273,8 +1273,8 @@ static void fn_out_consume(void *priv, char *line, unsigned long len)
}
diff_words_flush(ecbdata);
if (ecbdata->diff_words->type == DIFF_WORDS_PORCELAIN) {
- emit_line(ecbdata->opt, context, reset, line, len);
- fputs("~\n", ecbdata->opt->file);
+ emit_line(o, context, reset, line, len);
+ fputs("~\n", o->file);
} else {
/*
* Skip the prefix character, if any. With
@@ -1285,7 +1285,7 @@ static void fn_out_consume(void *priv, char *line, unsigned long len)
line++;
len--;
}
- emit_line(ecbdata->opt, context, reset, line, len);
+ emit_line(o, context, reset, line, len);
}
return;
}
@@ -1307,8 +1307,7 @@ static void fn_out_consume(void *priv, char *line, unsigned long len)
default:
/* incomplete line at the end */
ecbdata->lno_in_preimage++;
- emit_line(ecbdata->opt,
- diff_get_color(ecbdata->color_diff, DIFF_CONTEXT),
+ emit_line(o, diff_get_color(ecbdata->color_diff, DIFF_CONTEXT),
reset, line, len);
break;
}
@@ -1924,8 +1923,8 @@ static void show_dirstat(struct diff_options *options)
name = p->two->path ? p->two->path : p->one->path;
- if (p->one->sha1_valid && p->two->sha1_valid)
- content_changed = hashcmp(p->one->sha1, p->two->sha1);
+ if (p->one->oid_valid && p->two->oid_valid)
+ content_changed = oidcmp(&p->one->oid, &p->two->oid);
else
content_changed = 1;
@@ -2297,7 +2296,8 @@ static void builtin_diff(const char *name_a,
const char *add = diff_get_color_opt(o, DIFF_FILE_NEW);
show_submodule_summary(o->file, one->path ? one->path : two->path,
line_prefix,
- one->sha1, two->sha1, two->dirty_submodule,
+ one->oid.hash, two->oid.hash,
+ two->dirty_submodule,
meta, del, add, reset);
return;
}
@@ -2375,7 +2375,7 @@ static void builtin_diff(const char *name_a,
if (!one->data && !two->data &&
S_ISREG(one->mode) && S_ISREG(two->mode) &&
!DIFF_OPT_TST(o, BINARY)) {
- if (!hashcmp(one->sha1, two->sha1)) {
+ if (!oidcmp(&one->oid, &two->oid)) {
if (must_show_header)
fprintf(o->file, "%s", header.buf);
goto free_ab_and_return;
@@ -2428,7 +2428,6 @@ static void builtin_diff(const char *name_a,
memset(&ecbdata, 0, sizeof(ecbdata));
ecbdata.label_path = lbl;
ecbdata.color_diff = want_color(o->use_color);
- ecbdata.found_changesp = &o->found_changes;
ecbdata.ws_rule = whitespace_rule(name_b);
if (ecbdata.ws_rule & WS_BLANK_AT_EOF)
check_blank_at_eof(&mf1, &mf2, &ecbdata);
@@ -2496,7 +2495,7 @@ static void builtin_diffstat(const char *name_a, const char *name_b,
return;
}
- same_contents = !hashcmp(one->sha1, two->sha1);
+ same_contents = !oidcmp(&one->oid, &two->oid);
if (diff_filespec_is_binary(one) || diff_filespec_is_binary(two)) {
data->is_binary = 1;
@@ -2608,12 +2607,9 @@ static void builtin_checkdiff(const char *name_a, const char *name_b,
struct diff_filespec *alloc_filespec(const char *path)
{
- int namelen = strlen(path);
- struct diff_filespec *spec = xmalloc(sizeof(*spec) + namelen + 1);
+ struct diff_filespec *spec;
- memset(spec, 0, sizeof(*spec));
- spec->path = (char *)(spec + 1);
- memcpy(spec->path, path, namelen+1);
+ FLEXPTR_ALLOC_STR(spec, path, path);
spec->count = 1;
spec->is_binary = -1;
return spec;
@@ -2632,8 +2628,8 @@ void fill_filespec(struct diff_filespec *spec, const unsigned char *sha1,
{
if (mode) {
spec->mode = canon_mode(mode);
- hashcpy(spec->sha1, sha1);
- spec->sha1_valid = sha1_valid;
+ hashcpy(spec->oid.hash, sha1);
+ spec->oid_valid = sha1_valid;
}
}
@@ -2676,6 +2672,13 @@ static int reuse_worktree_file(const char *name, const unsigned char *sha1, int
if (!FAST_WORKING_DIRECTORY && !want_file && has_sha1_pack(sha1))
return 0;
+ /*
+ * Similarly, if we'd have to convert the file contents anyway, that
+ * makes the optimization not worthwhile.
+ */
+ if (!want_file && would_convert_to_git(name))
+ return 0;
+
len = strlen(name);
pos = cache_name_pos(name, len);
if (pos < 0)
@@ -2708,21 +2711,22 @@ static int reuse_worktree_file(const char *name, const unsigned char *sha1, int
static int diff_populate_gitlink(struct diff_filespec *s, int size_only)
{
- int len;
- char *data = xmalloc(100), *dirty = "";
+ struct strbuf buf = STRBUF_INIT;
+ char *dirty = "";
/* Are we looking at the work tree? */
if (s->dirty_submodule)
dirty = "-dirty";
- len = snprintf(data, 100,
- "Subproject commit %s%s\n", sha1_to_hex(s->sha1), dirty);
- s->data = data;
- s->size = len;
- s->should_free = 1;
+ strbuf_addf(&buf, "Subproject commit %s%s\n",
+ oid_to_hex(&s->oid), dirty);
+ s->size = buf.len;
if (size_only) {
s->data = NULL;
- free(data);
+ strbuf_release(&buf);
+ } else {
+ s->data = strbuf_detach(&buf, NULL);
+ s->should_free = 1;
}
return 0;
}
@@ -2758,8 +2762,8 @@ int diff_populate_filespec(struct diff_filespec *s, unsigned int flags)
if (S_ISGITLINK(s->mode))
return diff_populate_gitlink(s, size_only);
- if (!s->sha1_valid ||
- reuse_worktree_file(s->path, s->sha1, 0)) {
+ if (!s->oid_valid ||
+ reuse_worktree_file(s->path, s->oid.hash, 0)) {
struct strbuf buf = STRBUF_INIT;
struct stat st;
int fd;
@@ -2816,9 +2820,10 @@ int diff_populate_filespec(struct diff_filespec *s, unsigned int flags)
else {
enum object_type type;
if (size_only || (flags & CHECK_BINARY)) {
- type = sha1_object_info(s->sha1, &s->size);
+ type = sha1_object_info(s->oid.hash, &s->size);
if (type < 0)
- die("unable to read %s", sha1_to_hex(s->sha1));
+ die("unable to read %s",
+ oid_to_hex(&s->oid));
if (size_only)
return 0;
if (s->size > big_file_threshold && s->is_binary == -1) {
@@ -2826,9 +2831,9 @@ int diff_populate_filespec(struct diff_filespec *s, unsigned int flags)
return 0;
}
}
- s->data = read_sha1_file(s->sha1, &type, &s->size);
+ s->data = read_sha1_file(s->oid.hash, &type, &s->size);
if (!s->data)
- die("unable to read %s", sha1_to_hex(s->sha1));
+ die("unable to read %s", oid_to_hex(&s->oid));
s->should_free = 1;
}
return 0;
@@ -2857,7 +2862,7 @@ void diff_free_filespec_data(struct diff_filespec *s)
static void prep_temp_blob(const char *path, struct diff_tempfile *temp,
void *blob,
unsigned long size,
- const unsigned char *sha1,
+ const struct object_id *oid,
int mode)
{
int fd;
@@ -2882,9 +2887,8 @@ static void prep_temp_blob(const char *path, struct diff_tempfile *temp,
die_errno("unable to write temp-file");
close_tempfile(&temp->tempfile);
temp->name = get_tempfile_path(&temp->tempfile);
- strcpy(temp->hex, sha1_to_hex(sha1));
- temp->hex[40] = 0;
- sprintf(temp->mode, "%06o", mode);
+ oid_to_hex_r(temp->hex, oid);
+ xsnprintf(temp->mode, sizeof(temp->mode), "%06o", mode);
strbuf_release(&buf);
strbuf_release(&template);
free(path_dup);
@@ -2901,14 +2905,14 @@ static struct diff_tempfile *prepare_temp_file(const char *name,
* a '+' entry produces this for file-1.
*/
temp->name = "/dev/null";
- strcpy(temp->hex, ".");
- strcpy(temp->mode, ".");
+ xsnprintf(temp->hex, sizeof(temp->hex), ".");
+ xsnprintf(temp->mode, sizeof(temp->mode), ".");
return temp;
}
if (!S_ISGITLINK(one->mode) &&
- (!one->sha1_valid ||
- reuse_worktree_file(name, one->sha1, 1))) {
+ (!one->oid_valid ||
+ reuse_worktree_file(name, one->oid.hash, 1))) {
struct stat st;
if (lstat(name, &st) < 0) {
if (errno == ENOENT)
@@ -2920,26 +2924,26 @@ static struct diff_tempfile *prepare_temp_file(const char *name,
if (strbuf_readlink(&sb, name, st.st_size) < 0)
die_errno("readlink(%s)", name);
prep_temp_blob(name, temp, sb.buf, sb.len,
- (one->sha1_valid ?
- one->sha1 : null_sha1),
- (one->sha1_valid ?
+ (one->oid_valid ?
+ &one->oid : &null_oid),
+ (one->oid_valid ?
one->mode : S_IFLNK));
strbuf_release(&sb);
}
else {
/* we can borrow from the file in the work tree */
temp->name = name;
- if (!one->sha1_valid)
- strcpy(temp->hex, sha1_to_hex(null_sha1));
+ if (!one->oid_valid)
+ sha1_to_hex_r(temp->hex, null_sha1);
else
- strcpy(temp->hex, sha1_to_hex(one->sha1));
+ sha1_to_hex_r(temp->hex, one->oid.hash);
/* Even though we may sometimes borrow the
* contents from the work tree, we always want
* one->mode. mode is trustworthy even when
* !(one->sha1_valid), as long as
* DIFF_FILE_VALID(one).
*/
- sprintf(temp->mode, "%06o", one->mode);
+ xsnprintf(temp->mode, sizeof(temp->mode), "%06o", one->mode);
}
return temp;
}
@@ -2947,7 +2951,7 @@ static struct diff_tempfile *prepare_temp_file(const char *name,
if (diff_populate_filespec(one, 0))
die("cannot read data blob for %s", one->path);
prep_temp_blob(name, temp, one->data, one->size,
- one->sha1, one->mode);
+ &one->oid, one->mode);
}
return temp;
}
@@ -3060,7 +3064,7 @@ static void fill_metainfo(struct strbuf *msg,
default:
*must_show_header = 0;
}
- if (one && two && hashcmp(one->sha1, two->sha1)) {
+ if (one && two && oidcmp(&one->oid, &two->oid)) {
int abbrev = DIFF_OPT_TST(o, FULL_INDEX) ? 40 : DEFAULT_ABBREV;
if (DIFF_OPT_TST(o, BINARY)) {
@@ -3070,8 +3074,8 @@ static void fill_metainfo(struct strbuf *msg,
abbrev = 40;
}
strbuf_addf(msg, "%s%sindex %s..", line_prefix, set,
- find_unique_abbrev(one->sha1, abbrev));
- strbuf_addstr(msg, find_unique_abbrev(two->sha1, abbrev));
+ find_unique_abbrev(one->oid.hash, abbrev));
+ strbuf_addstr(msg, find_unique_abbrev(two->oid.hash, abbrev));
if (one->mode == two->mode)
strbuf_addf(msg, " %06o", one->mode);
strbuf_addf(msg, "%s\n", reset);
@@ -3126,20 +3130,20 @@ static void run_diff_cmd(const char *pgm,
static void diff_fill_sha1_info(struct diff_filespec *one)
{
if (DIFF_FILE_VALID(one)) {
- if (!one->sha1_valid) {
+ if (!one->oid_valid) {
struct stat st;
if (one->is_stdin) {
- hashcpy(one->sha1, null_sha1);
+ oidclr(&one->oid);
return;
}
if (lstat(one->path, &st) < 0)
die_errno("stat '%s'", one->path);
- if (index_path(one->sha1, one->path, &st, 0))
+ if (index_path(one->oid.hash, one->path, &st, 0))
die("cannot hash %s", one->path);
}
}
else
- hashclr(one->sha1);
+ oidclr(&one->oid);
}
static void strip_prefix(int prefix_length, const char **namep, const char **otherp)
@@ -3278,6 +3282,8 @@ void diff_setup(struct diff_options *options)
options->use_color = diff_use_color_default;
options->detect_rename = diff_detect_rename_default;
options->xdl_opts |= diff_algorithm;
+ if (diff_compaction_heuristic)
+ DIFF_XDL_SET(options, COMPACTION_HEURISTIC);
options->orderfile = diff_order_file_cfg;
@@ -3695,12 +3701,16 @@ static int parse_ws_error_highlight(struct diff_options *opt, const char *arg)
return 1;
}
-int diff_opt_parse(struct diff_options *options, const char **av, int ac)
+int diff_opt_parse(struct diff_options *options,
+ const char **av, int ac, const char *prefix)
{
const char *arg = av[0];
const char *optarg;
int argcount;
+ if (!prefix)
+ prefix = "";
+
/* Output format options */
if (!strcmp(arg, "-p") || !strcmp(arg, "-u") || !strcmp(arg, "--patch")
|| opt_arg(arg, 'U', "unified", &options->context))
@@ -3794,6 +3804,10 @@ int diff_opt_parse(struct diff_options *options, const char **av, int ac)
DIFF_XDL_SET(options, IGNORE_WHITESPACE_AT_EOL);
else if (!strcmp(arg, "--ignore-blank-lines"))
DIFF_XDL_SET(options, IGNORE_BLANK_LINES);
+ else if (!strcmp(arg, "--compaction-heuristic"))
+ DIFF_XDL_SET(options, COMPACTION_HEURISTIC);
+ else if (!strcmp(arg, "--no-compaction-heuristic"))
+ DIFF_XDL_CLR(options, COMPACTION_HEURISTIC);
else if (!strcmp(arg, "--patience"))
options->xdl_opts = DIFF_WITH_ALG(options, PATIENCE_DIFF);
else if (!strcmp(arg, "--histogram"))
@@ -3917,7 +3931,8 @@ int diff_opt_parse(struct diff_options *options, const char **av, int ac)
else if (!strcmp(arg, "--pickaxe-regex"))
options->pickaxe_opts |= DIFF_PICKAXE_REGEX;
else if ((argcount = short_opt('O', av, &optarg))) {
- options->orderfile = optarg;
+ const char *path = prefix_filename(prefix, strlen(prefix), optarg);
+ options->orderfile = xstrdup(path);
return argcount;
}
else if ((argcount = parse_long_opt("diff-filter", av, &optarg))) {
@@ -3956,10 +3971,13 @@ int diff_opt_parse(struct diff_options *options, const char **av, int ac)
else if (!strcmp(arg, "--no-function-context"))
DIFF_OPT_CLR(options, FUNCCONTEXT);
else if ((argcount = parse_long_opt("output", av, &optarg))) {
- options->file = fopen(optarg, "w");
+ const char *path = prefix_filename(prefix, strlen(prefix), optarg);
+ options->file = fopen(path, "w");
if (!options->file)
- die_errno("Could not open '%s'", optarg);
+ die_errno("Could not open '%s'", path);
options->close_file = 1;
+ if (options->use_color != GIT_COLOR_ALWAYS)
+ options->use_color = GIT_COLOR_NEVER;
return argcount;
} else
return 0;
@@ -4085,9 +4103,9 @@ const char *diff_unique_abbrev(const unsigned char *sha1, int len)
if (abblen < 37) {
static char hex[41];
if (len < abblen && abblen <= len + 2)
- sprintf(hex, "%s%.*s", abbrev, len+3-abblen, "..");
+ xsnprintf(hex, sizeof(hex), "%s%.*s", abbrev, len+3-abblen, "..");
else
- sprintf(hex, "%s...", abbrev);
+ xsnprintf(hex, sizeof(hex), "%s...", abbrev);
return hex;
}
return sha1_to_hex(sha1);
@@ -4101,8 +4119,9 @@ static void diff_flush_raw(struct diff_filepair *p, struct diff_options *opt)
fprintf(opt->file, "%s", diff_line_prefix(opt));
if (!(opt->output_format & DIFF_FORMAT_NAME_STATUS)) {
fprintf(opt->file, ":%06o %06o %s ", p->one->mode, p->two->mode,
- diff_unique_abbrev(p->one->sha1, opt->abbrev));
- fprintf(opt->file, "%s ", diff_unique_abbrev(p->two->sha1, opt->abbrev));
+ diff_unique_abbrev(p->one->oid.hash, opt->abbrev));
+ fprintf(opt->file, "%s ",
+ diff_unique_abbrev(p->two->oid.hash, opt->abbrev));
}
if (p->score) {
fprintf(opt->file, "%c%03d%c", p->status, similarity_index(p),
@@ -4151,11 +4170,11 @@ int diff_unmodified_pair(struct diff_filepair *p)
/* both are valid and point at the same path. that is, we are
* dealing with a change.
*/
- if (one->sha1_valid && two->sha1_valid &&
- !hashcmp(one->sha1, two->sha1) &&
+ if (one->oid_valid && two->oid_valid &&
+ !oidcmp(&one->oid, &two->oid) &&
!one->dirty_submodule && !two->dirty_submodule)
return 1; /* no change */
- if (!one->sha1_valid && !two->sha1_valid)
+ if (!one->oid_valid && !two->oid_valid)
return 1; /* both look at the same file on the filesystem. */
return 0;
}
@@ -4216,7 +4235,7 @@ void diff_debug_filespec(struct diff_filespec *s, int x, const char *one)
s->path,
DIFF_FILE_VALID(s) ? "valid" : "invalid",
s->mode,
- s->sha1_valid ? sha1_to_hex(s->sha1) : "");
+ s->oid_valid ? oid_to_hex(&s->oid) : "");
fprintf(stderr, "queue[%d] %s size %lu\n",
x, one ? one : "",
s->size);
@@ -4286,11 +4305,11 @@ static void diff_resolve_rename_copy(void)
else
p->status = DIFF_STATUS_RENAMED;
}
- else if (hashcmp(p->one->sha1, p->two->sha1) ||
+ else if (oidcmp(&p->one->oid, &p->two->oid) ||
p->one->mode != p->two->mode ||
p->one->dirty_submodule ||
p->two->dirty_submodule ||
- is_null_sha1(p->one->sha1))
+ is_null_oid(&p->one->oid))
p->status = DIFF_STATUS_MODIFIED;
else {
/* This is a "no-change" entry and should not
@@ -4432,7 +4451,7 @@ static void patch_id_consume(void *priv, char *line, unsigned long len)
}
/* returns 0 upon success, and writes result into sha1 */
-static int diff_get_patch_id(struct diff_options *options, unsigned char *sha1)
+static int diff_get_patch_id(struct diff_options *options, unsigned char *sha1, int diff_header_only)
{
struct diff_queue_struct *q = &diff_queued_diff;
int i;
@@ -4467,9 +4486,6 @@ static int diff_get_patch_id(struct diff_options *options, unsigned char *sha1)
diff_fill_sha1_info(p->one);
diff_fill_sha1_info(p->two);
- if (fill_mmfile(&mf1, p->one) < 0 ||
- fill_mmfile(&mf2, p->two) < 0)
- return error("unable to read files to diff");
len1 = remove_space(p->one->path, strlen(p->one->path));
len2 = remove_space(p->two->path, strlen(p->two->path));
@@ -4504,10 +4520,19 @@ static int diff_get_patch_id(struct diff_options *options, unsigned char *sha1)
len2, p->two->path);
git_SHA1_Update(&ctx, buffer, len1);
+ if (diff_header_only)
+ continue;
+
+ if (fill_mmfile(&mf1, p->one) < 0 ||
+ fill_mmfile(&mf2, p->two) < 0)
+ return error("unable to read files to diff");
+
if (diff_filespec_is_binary(p->one) ||
diff_filespec_is_binary(p->two)) {
- git_SHA1_Update(&ctx, sha1_to_hex(p->one->sha1), 40);
- git_SHA1_Update(&ctx, sha1_to_hex(p->two->sha1), 40);
+ git_SHA1_Update(&ctx, oid_to_hex(&p->one->oid),
+ 40);
+ git_SHA1_Update(&ctx, oid_to_hex(&p->two->oid),
+ 40);
continue;
}
@@ -4524,11 +4549,11 @@ static int diff_get_patch_id(struct diff_options *options, unsigned char *sha1)
return 0;
}
-int diff_flush_patch_id(struct diff_options *options, unsigned char *sha1)
+int diff_flush_patch_id(struct diff_options *options, unsigned char *sha1, int diff_header_only)
{
struct diff_queue_struct *q = &diff_queued_diff;
int i;
- int result = diff_get_patch_id(options, sha1);
+ int result = diff_get_patch_id(options, sha1, diff_header_only);
for (i = 0; i < q->nr; i++)
diff_free_filepair(q->queue[i]);
@@ -4799,7 +4824,7 @@ static int diff_filespec_check_stat_unmatch(struct diff_filepair *p)
*/
if (!DIFF_FILE_VALID(p->one) || /* (1) */
!DIFF_FILE_VALID(p->two) ||
- (p->one->sha1_valid && p->two->sha1_valid) ||
+ (p->one->oid_valid && p->two->oid_valid) ||
(p->one->mode != p->two->mode) ||
diff_populate_filespec(p->one, CHECK_SIZE_ONLY) ||
diff_populate_filespec(p->two, CHECK_SIZE_ONLY) ||
@@ -5081,7 +5106,7 @@ size_t fill_textconv(struct userdiff_driver *driver,
{
size_t size;
- if (!driver || !driver->textconv) {
+ if (!driver) {
if (!DIFF_FILE_VALID(df)) {
*outbuf = "";
return 0;
@@ -5092,8 +5117,12 @@ size_t fill_textconv(struct userdiff_driver *driver,
return df->size;
}
- if (driver->textconv_cache && df->sha1_valid) {
- *outbuf = notes_cache_get(driver->textconv_cache, df->sha1,
+ if (!driver->textconv)
+ die("BUG: fill_textconv called with non-textconv driver");
+
+ if (driver->textconv_cache && df->oid_valid) {
+ *outbuf = notes_cache_get(driver->textconv_cache,
+ df->oid.hash,
&size);
if (*outbuf)
return size;
@@ -5103,9 +5132,9 @@ size_t fill_textconv(struct userdiff_driver *driver,
if (!*outbuf)
die("unable to read files to diff");
- if (driver->textconv_cache && df->sha1_valid) {
+ if (driver->textconv_cache && df->oid_valid) {
/* ignore errors, as we might be in a readonly repository */
- notes_cache_put(driver->textconv_cache, df->sha1, *outbuf,
+ notes_cache_put(driver->textconv_cache, df->oid.hash, *outbuf,
size);
/*
* we could save up changes and flush them all at the end,