commit - e4d984c230e887c67692cfcbb7624ab2ccf95e2d
commit + c932eeeb83c00ba282780d657b539e342d092311
blob - 813c2606897283a1597ed1e26f0709ae9ddd2df2
blob + c0b4a22f88ac66488a7663be09009008dd5b3cd0
--- lib/worktree.c
+++ lib/worktree.c
}
return err;
}
+
+struct bump_base_commit_id_arg {
+ struct got_object_id *base_commit_id;
+ const char *path;
+ size_t path_len;
+ const char *entry_name;
+};
+/* Bump base commit ID of all files within an updated part of the work tree. */
+static const struct got_error *
+bump_base_commit_id(void *arg, struct got_fileindex_entry *ie)
+{
+ struct bump_base_commit_id_arg *a = arg;
+
+ if (a->entry_name) {
+ if (strcmp(ie->path, a->path) != 0)
+ return NULL;
+ } else if (!got_path_is_child(ie->path, a->path, a->path_len))
+ return NULL;
+
+ memcpy(ie->commit_sha1, a->base_commit_id->sha1, SHA1_DIGEST_LENGTH);
+ return NULL;
+}
+
const struct got_error *
got_worktree_checkout_files(struct got_worktree *worktree, const char *path,
struct got_repository *repo, got_worktree_checkout_cb progress_cb,
checkout_err = got_fileindex_diff_tree(fileindex, tree, relpath,
entry_name, repo, &diff_cb, &arg);
+ if (checkout_err == NULL) {
+ struct bump_base_commit_id_arg bbc_arg;
+ bbc_arg.base_commit_id = worktree->base_commit_id;
+ bbc_arg.entry_name = entry_name;
+ bbc_arg.path = path;
+ bbc_arg.path_len = strlen(path);
+ err = got_fileindex_for_each_entry_safe(fileindex,
+ bump_base_commit_id, &bbc_arg);
+ if (err)
+ goto done;
+ }
+
/* Try to sync the fileindex back to disk in any case. */
err = got_fileindex_write(fileindex, new_index);
if (err)
blob - da703088394f8fa0cbbb0dfdeeb5ccd9a3bc0370
blob + 13de6ccc78b1fffae1913d1010e3af7708972c4e
--- regress/cmdline/update.sh
+++ regress/cmdline/update.sh
test_done "$testroot" "$ret"
}
+
+function test_update_bumps_base_commit_id {
+ local testroot=`test_init update_to_commit_on_wrong_branch`
+
+ got checkout $testroot/repo $testroot/wt > /dev/null
+ ret="$?"
+ if [ "$ret" != "0" ]; then
+ test_done "$testroot" "$ret"
+ return 1
+ fi
+ echo "modified alpha" > $testroot/wt/alpha
+ (cd $testroot/wt && got commit -m "changed alpha" > $testroot/stdout)
+
+ local head_rev=`git_show_head $testroot/repo`
+ echo "M alpha" > $testroot/stdout.expected
+ echo "created commit $head_rev" >> $testroot/stdout.expected
+ cmp -s $testroot/stdout.expected $testroot/stdout
+ ret="$?"
+ if [ "$ret" != "0" ]; then
+ diff -u $testroot/stdout.expected $testroot/stdout
+ test_done "$testroot" "$ret"
+ return 1
+ fi
+
+ echo "modified beta" > $testroot/wt/beta
+ (cd $testroot/wt && got commit -m "changed beta" > $testroot/stdout \
+ 2> $testroot/stderr)
+
+ echo -n "" > $testroot/stdout.expected
+ echo "got: work tree must be updated before these changes can be committed" > $testroot/stderr.expected
+ cmp -s $testroot/stderr.expected $testroot/stderr
+ ret="$?"
+ if [ "$ret" != "0" ]; then
+ diff -u $testroot/stderr.expected $testroot/stderr
+ test_done "$testroot" "$ret"
+ return 1
+ fi
+
+ # XXX At present, got requires users to run 'update' after 'commit'.
+ (cd $testroot/wt && got update > $testroot/stdout)
+
+ echo "Already up-to-date" > $testroot/stdout.expected
+ cmp -s $testroot/stdout.expected $testroot/stdout
+ ret="$?"
+ if [ "$ret" != "0" ]; then
+ diff -u $testroot/stdout.expected $testroot/stdout
+ test_done "$testroot" "$ret"
+ return 1
+ fi
+
+ (cd $testroot/wt && got commit -m "changed beta" > $testroot/stdout)
+
+ local head_rev=`git_show_head $testroot/repo`
+ echo "M beta" > $testroot/stdout.expected
+ echo "created commit $head_rev" >> $testroot/stdout.expected
+ cmp -s $testroot/stdout.expected $testroot/stdout
+ ret="$?"
+ if [ "$ret" != "0" ]; then
+ diff -u $testroot/stdout.expected $testroot/stdout
+ test_done "$testroot" "$ret"
+ return 1
+ fi
+
+ test_done "$testroot" "$ret"
+}
+
run_test test_update_basic
run_test test_update_adds_file
run_test test_update_deletes_file
run_test test_update_moved_branch_ref
run_test test_update_to_another_branch
run_test test_update_to_commit_on_wrong_branch
+run_test test_update_bumps_base_commit_id