int git_branch_is_head( const git_reference *branch) { git_reference *head; bool is_same = false; int error; assert(branch); if (!git_reference_is_branch(branch)) return false; error = git_repository_head(&head, git_reference_owner(branch)); if (error == GIT_EUNBORNBRANCH || error == GIT_ENOTFOUND) return false; if (error < 0) return -1; is_same = strcmp( git_reference_name(branch), git_reference_name(head)) == 0; git_reference_free(head); return is_same; }
static int show_ref(git_reference *ref, void *data) { git_repository *repo = data; git_reference *resolved = NULL; char hex[GIT_OID_HEXSZ+1]; const git_oid *oid; git_object *obj; if (git_reference_type(ref) == GIT_REF_SYMBOLIC) check_lg2(git_reference_resolve(&resolved, ref), "Unable to resolve symbolic reference", git_reference_name(ref)); oid = git_reference_target(resolved ? resolved : ref); git_oid_fmt(hex, oid); hex[GIT_OID_HEXSZ] = 0; check_lg2(git_object_lookup(&obj, repo, oid, GIT_OBJ_ANY), "Unable to lookup object", hex); printf("%s %-6s\t%s\n", hex, git_object_type2string(git_object_type(obj)), git_reference_name(ref)); if (resolved) git_reference_free(resolved); return 0; }
int git_branch_is_head( git_reference *branch) { git_reference *head; bool is_same = false; int error; assert(branch); if (!git_reference_is_branch(branch)) return false; error = git_repository_head(&head, git_reference_owner(branch)); if (error == GIT_EORPHANEDHEAD) return false; if (error < 0) return -1; is_same = strcmp( git_reference_name(branch), git_reference_name(head)) == 0; git_reference_free(head); return is_same; }
static int retrieve_base_commit_and_message( git_commit **b_commit, git_buf *stash_message, git_repository *repo) { git_reference *head = NULL; int error; if ((error = retrieve_head(&head, repo)) < 0) return error; if (strcmp("HEAD", git_reference_name(head)) == 0) error = git_buf_puts(stash_message, "(no branch): "); else error = git_buf_printf( stash_message, "%s: ", git_reference_name(head) + strlen(GIT_REFS_HEADS_DIR)); if (error < 0) goto cleanup; if ((error = git_commit_lookup( b_commit, repo, git_reference_target(head))) < 0) goto cleanup; if ((error = append_commit_description(stash_message, *b_commit)) < 0) goto cleanup; cleanup: git_reference_free(head); return error; }
void test_refs_unicode__create_and_lookup(void) { git_reference *ref0, *ref1, *ref2; git_repository *repo2; const char *REFNAME = "refs/heads/" "\305" "ngstr" "\366" "m"; const char *master = "refs/heads/master"; /* Create the reference */ cl_git_pass(git_reference_lookup(&ref0, repo, master)); cl_git_pass(git_reference_create_oid(&ref1, repo, REFNAME, git_reference_oid(ref0), 0)); cl_assert(strcmp(REFNAME, git_reference_name(ref1)) == 0); /* Lookup the reference in a different instance of the repository */ cl_git_pass(git_repository_open(&repo2, "testrepo.git")); cl_git_pass(git_reference_lookup(&ref2, repo2, REFNAME)); cl_assert(git_oid_cmp(git_reference_oid(ref1), git_reference_oid(ref2)) == 0); cl_assert(strcmp(REFNAME, git_reference_name(ref2)) == 0); git_reference_free(ref0); git_reference_free(ref1); git_reference_free(ref2); git_repository_free(repo2); }
static int retrieve_oid_from_reflog(git_oid *oid, git_reference *ref, size_t identifier) { git_reflog *reflog; int error = -1; size_t numentries; const git_reflog_entry *entry; bool search_by_pos = (identifier <= 100000000); if (git_reflog_read(&reflog, git_reference_owner(ref), git_reference_name(ref)) < 0) return -1; numentries = git_reflog_entrycount(reflog); if (search_by_pos) { if (numentries < identifier + 1) { giterr_set( GITERR_REFERENCE, "Reflog for '%s' has only %"PRIuZ" entries, asked for %"PRIuZ, git_reference_name(ref), numentries, identifier); error = GIT_ENOTFOUND; goto cleanup; } entry = git_reflog_entry_byindex(reflog, identifier); git_oid_cpy(oid, git_reflog_entry_id_new(entry)); error = 0; goto cleanup; } else { size_t i; git_time commit_time; for (i = 0; i < numentries; i++) { entry = git_reflog_entry_byindex(reflog, i); commit_time = git_reflog_entry_committer(entry)->when; if (commit_time.time > (git_time_t)identifier) continue; git_oid_cpy(oid, git_reflog_entry_id_new(entry)); error = 0; goto cleanup; } error = GIT_ENOTFOUND; } cleanup: git_reflog_free(reflog); return error; }
int git_branch_move( git_reference **out, git_reference *branch, const char *new_branch_name, int force) { git_buf new_reference_name = GIT_BUF_INIT, old_config_section = GIT_BUF_INIT, new_config_section = GIT_BUF_INIT, log_message = GIT_BUF_INIT; int error; assert(branch && new_branch_name); if (!git_reference_is_branch(branch)) return not_a_local_branch(git_reference_name(branch)); if ((error = git_buf_joinpath(&new_reference_name, GIT_REFS_HEADS_DIR, new_branch_name)) < 0) goto done; if ((error = git_buf_printf(&log_message, "branch: renamed %s to %s", git_reference_name(branch), git_buf_cstr(&new_reference_name))) < 0) goto done; /* first update ref then config so failure won't trash config */ error = git_reference_rename( out, branch, git_buf_cstr(&new_reference_name), force, git_buf_cstr(&log_message)); if (error < 0) goto done; git_buf_join(&old_config_section, '.', "branch", git_reference_name(branch) + strlen(GIT_REFS_HEADS_DIR)); git_buf_join(&new_config_section, '.', "branch", new_branch_name); error = git_config_rename_section( git_reference_owner(branch), git_buf_cstr(&old_config_section), git_buf_cstr(&new_config_section)); done: git_buf_free(&new_reference_name); git_buf_free(&old_config_section); git_buf_free(&new_config_section); git_buf_free(&log_message); return error; }
const char * branchname(git_repository * repo){ git_reference * head; head = repo_head(repo); const char * branchname; branchname = git_reference_name(head); return branchname; }
/* * call-seq: * reference.log -> [reflog_entry, ...] * * Return an array with the log of all modifications to this reference * * Each +reflog_entry+ is a hash with the following keys: * * - +:id_old+: previous OID before the change * - +:id_new+: OID after the change * - +:committer+: author of the change * - +:message+: message for the change * * Example: * * reference.log #=> [ * # { * # :id_old => nil, * # :id_new => '9d09060c850defbc7711d08b57def0d14e742f4e', * # :committer => {:name => 'Vicent Marti', :email => {'*****@*****.**'}}, * # :message => 'created reference' * # }, ... ] */ static VALUE rb_git_reflog(VALUE self) { git_reflog *reflog; git_reference *ref; int error; VALUE rb_log; size_t i, ref_count; Data_Get_Struct(self, git_reference, ref); error = git_reflog_read(&reflog, git_reference_owner(ref), git_reference_name(ref)); rugged_exception_check(error); ref_count = git_reflog_entrycount(reflog); rb_log = rb_ary_new2(ref_count); for (i = 0; i < ref_count; ++i) { const git_reflog_entry *entry = git_reflog_entry_byindex(reflog, ref_count - i - 1); rb_ary_push(rb_log, reflog_entry_new(entry)); } git_reflog_free(reflog); return rb_log; }
void test_network_remote_rename__overwrite_ref_in_target(void) { git_oid id; char idstr[GIT_OID_HEXSZ + 1] = {0}; git_reference *ref; git_branch_t btype; git_branch_iterator *iter; git_strarray problems = {0}; cl_git_pass(git_oid_fromstr(&id, "a65fedf39aefe402d3bb6e24df4d4f5fe4547750")); cl_git_pass(git_reference_create(&ref, _repo, "refs/remotes/renamed/master", &id, 1, NULL, NULL)); git_reference_free(ref); cl_git_pass(git_remote_rename(&problems, _repo, _remote_name, "renamed")); cl_assert_equal_i(0, problems.count); git_strarray_free(&problems); /* make sure there's only one remote-tracking branch */ cl_git_pass(git_branch_iterator_new(&iter, _repo, GIT_BRANCH_REMOTE)); cl_git_pass(git_branch_next(&ref, &btype, iter)); cl_assert_equal_s("refs/remotes/renamed/master", git_reference_name(ref)); git_oid_fmt(idstr, git_reference_target(ref)); cl_assert_equal_s("be3563ae3f795b2b4353bcce3a527ad0a4f7f644", idstr); git_reference_free(ref); cl_git_fail_with(GIT_ITEROVER, git_branch_next(&ref, &btype, iter)); git_branch_iterator_free(iter); }
static int update_head_to_new_branch( git_repository *repo, const git_oid *target, const char *name, const git_signature *signature, const char *reflog_message) { git_reference *tracking_branch = NULL; int error; if (!git__prefixcmp(name, GIT_REFS_HEADS_DIR)) name += strlen(GIT_REFS_HEADS_DIR); error = create_tracking_branch(&tracking_branch, repo, target, name, signature, reflog_message); if (!error) error = git_repository_set_head( repo, git_reference_name(tracking_branch), signature, reflog_message); git_reference_free(tracking_branch); /* if it already existed, then the user's refspec created it for us, ignore it' */ if (error == GIT_EEXISTS) error = 0; return error; }
static int peel_error(int error, git_reference *ref, const char* msg) { giterr_set( GITERR_INVALID, "The reference '%s' cannot be peeled - %s", git_reference_name(ref), msg); return error; }
int git_branch_delete(git_repository *repo, const char *branch_name, git_branch_t branch_type) { git_reference *branch = NULL; git_reference *head = NULL; int error; assert((branch_type == GIT_BRANCH_LOCAL) || (branch_type == GIT_BRANCH_REMOTE)); if ((error = retrieve_branch_reference(&branch, repo, branch_name, branch_type == GIT_BRANCH_REMOTE)) < 0) return error; if (git_reference_lookup(&head, repo, GIT_HEAD_FILE) < 0) { giterr_set(GITERR_REFERENCE, "Cannot locate HEAD."); goto on_error; } if ((git_reference_type(head) == GIT_REF_SYMBOLIC) && (strcmp(git_reference_target(head), git_reference_name(branch)) == 0)) { giterr_set(GITERR_REFERENCE, "Cannot delete branch '%s' as it is the current HEAD of the repository.", branch_name); goto on_error; } if (git_reference_delete(branch) < 0) goto on_error; git_reference_free(head); return 0; on_error: git_reference_free(head); git_reference_free(branch); return -1; }
Commit Commit::FromGitReference(const class Repository &repo, git_reference *ref) { git_oid oid; git_reference_name_to_id(&oid, repo.GetGitPointer(), git_reference_name(ref)); return Commit::FromGitOid(repo, oid); }
void CacheGitDirectory::updateRef() { currentGitRef_ = ""; git_repository *repo = NULL; git_reference *head = NULL; git_libgit2_init(); int r = git_repository_open(&repo, gitRepository_.c_str()); if (r != 0) { LOG(INFO) << "Cannot open git repository " << gitRepository_; goto cleanup; } if (git_repository_head_detached(repo)) { LOG(INFO) << "We are in detached state"; goto cleanup; } r = git_repository_head(&head, repo); if (r != 0) { LOG(INFO) << "Cannot get current ref head"; goto cleanup; } currentGitRef_ = git_reference_name(head); LOG(INFO) << "found ref: " << currentGitRef_; cleanup: git_repository_free(repo); git_libgit2_shutdown(); }
PyObject * Branch_upstream_name__get__(Branch *self) { int err; const char *branch_name; char *c_name = NULL; PyObject *py_name; CHECK_REFERENCE(self); branch_name = git_reference_name(self->reference); /* Get the length of the upstream name */ err = git_branch_upstream_name(NULL, 0, self->repo->repo, branch_name); if (err < GIT_OK) return Error_set(err); /* Get the actual upstream name */ c_name = calloc(err, sizeof(char)); if (c_name == NULL) return PyErr_NoMemory(); err = git_branch_upstream_name(c_name, err * sizeof(char), self->repo->repo, branch_name); if (err < GIT_OK) { free(c_name); return Error_set(err); } py_name = to_unicode(c_name, NULL, NULL); free(c_name); return py_name; }
static void mne_git_walk_tree(git_tree *tree, git_reference *ref, mne_git_walk_ctx *ctx) { ctx->distinct_blobs = 0; int ref_name_len = strlen(git_reference_name(ref)); ctx->ref_name = malloc(sizeof(char) * (ref_name_len + 1)); assert(ctx->ref_name != NULL); strncpy(ctx->ref_name, git_reference_name(ref), ref_name_len); ctx->ref_name[ref_name_len] = 0; ref_names[ctx->ref_index] = ctx->ref_name; printf(" * %-22s", ctx->ref_name); fflush(stdout); git_tree_walk(tree, &mne_git_tree_entry_cb, GIT_TREEWALK_POST, ctx); printf(" ✔ +%d\n", ctx->distinct_blobs); }
/** * ggit_reflog_rename: * @reflog: a #GgitReflog. * @new_name: the new name of the reference. * @error: a #GError for error reporting, or %NULL. * * Renames the reflog for to @new_name, on error @error is set. */ gboolean ggit_reflog_rename (GgitReflog *reflog, const gchar *new_name, GError **error) { git_reference *nref; gint ret; g_return_val_if_fail (reflog != NULL, FALSE); g_return_val_if_fail (new_name != NULL && *new_name != '\0', FALSE); g_return_val_if_fail (error == NULL || *error == NULL, FALSE); nref = _ggit_native_get (reflog->ref); ret = git_reflog_rename (git_reference_owner (nref), git_reference_name (nref), new_name); if (ret != GIT_OK) { _ggit_error_set (error, ret); return FALSE; } return TRUE; }
/** * ggit_ref_get_log: * @ref: a #GgitRef. * @error: a #GError for error reporting, or %NULL. * * Gets the #GgitReflog for @ref. The reflog will be created if it doesn't exist * yet. * * Returns: (transfer full): the reflog. */ GgitReflog * ggit_ref_get_log (GgitRef *ref, GError **error) { git_reflog *reflog; git_reference *nref; gint ret; g_return_val_if_fail (GGIT_IS_REF (ref), NULL); g_return_val_if_fail (error == NULL || *error == NULL, NULL); nref = _ggit_native_get (ref); ret = git_reflog_read (&reflog, git_reference_owner (nref), git_reference_name (nref)); if (ret != GIT_OK) { _ggit_error_set (error, ret); return NULL; } return _ggit_reflog_wrap (ref, reflog); }
/** * ggit_ref_get_name: * @ref: a #GgitRef. * * Gets the full name of @ref. * * Returns: the full name of a reference. */ const gchar * ggit_ref_get_name (GgitRef *ref) { g_return_val_if_fail (ref != NULL, NULL); return git_reference_name (_ggit_native_get (ref)); }
void test_refs_branches_move__can_move_with_unicode(void) { git_reference *original_ref, *new_ref; const char *new_branch_name = "\x41\xCC\x8A\x73\x74\x72\x6F\xCC\x88\x6D"; cl_git_pass(git_reference_lookup(&original_ref, repo, "refs/heads/br2")); cl_git_pass(git_branch_move(&new_ref, original_ref, new_branch_name, 0)); if (cl_repo_get_bool(repo, "core.precomposeunicode")) cl_assert_equal_s(GIT_REFS_HEADS_DIR "\xC3\x85\x73\x74\x72\xC3\xB6\x6D", git_reference_name(new_ref)); else cl_assert_equal_s(GIT_REFS_HEADS_DIR "\x41\xCC\x8A\x73\x74\x72\x6F\xCC\x88\x6D", git_reference_name(new_ref)); git_reference_free(original_ref); git_reference_free(new_ref); }
/** * ggit_branch_get_upstream: * @branch: a #GgitBranch. * @error: a #GError for error reporting, or %NULL. * * Gets the reference supporting the remote tracking branch, * given a local branch reference. * * Returns: (transfer full) (allow-none): the reference supporting the remote tracking branch. */ GgitRef * ggit_branch_get_upstream (GgitBranch *branch, GError **error) { gint ret; git_reference *upstream; const gchar *name; GgitRef *ref; g_return_val_if_fail (GGIT_IS_BRANCH (branch), NULL); g_return_val_if_fail (error == NULL || *error == NULL, NULL); ret = git_branch_upstream (&upstream, _ggit_native_get (branch)); if (ret != GIT_OK) { _ggit_error_set (error, ret); return NULL; } name = git_reference_name (_ggit_native_get (upstream)); if (g_str_has_prefix (name, "refs/heads/")) { ref = GGIT_REF (_ggit_branch_wrap (upstream)); } else { ref = _ggit_ref_wrap (upstream); } return ref; }
static int update_remote(git_repository *repo, git_remote *origin, git_reference *local, git_reference *remote, enum remote_transport rt) { UNUSED(repo); UNUSED(remote); git_push_options opts = GIT_PUSH_OPTIONS_INIT; git_strarray refspec; const char *name = git_reference_name(local); if (verbose) fprintf(stderr, "git storage: update remote\n"); refspec.count = 1; refspec.strings = (char **)&name; auth_attempt = 0; opts.callbacks.push_transfer_progress = &push_transfer_progress_cb; if (rt == RT_SSH) opts.callbacks.credentials = credential_ssh_cb; else if (rt == RT_HTTPS) opts.callbacks.credentials = credential_https_cb; opts.callbacks.certificate_check = certificate_check_cb; if (git_remote_push(origin, &refspec, &opts)) { if (is_subsurface_cloud) return report_error(translate("gettextFromC", "Could not update Subsurface cloud storage, try again later")); else return report_error("Unable to update remote with current local cache state (%s)", giterr_last()->message); } return 0; }
void test_refs_branches_create__can_force_create_over_an_existing_branch(void) { retrieve_known_commit(&target, repo); cl_git_pass(git_branch_create(&branch, repo, "br2", target, 1, NULL, NULL)); cl_git_pass(git_oid_cmp(git_reference_target(branch), git_commit_id(target))); cl_assert_equal_s("refs/heads/br2", git_reference_name(branch)); }
void test_refs_branches_tracking__can_retrieve_the_local_tracking_reference_of_a_local_branch(void) { cl_git_pass(git_reference_lookup(&branch, repo, "refs/heads/track-local")); cl_git_pass(git_branch_tracking(&tracking, branch)); cl_assert_equal_s("refs/heads/master", git_reference_name(tracking)); }
void assert_conflict( const char *entry_path, const char *new_content, const char *parent_sha, const char *commit_sha) { git_index *index; git_object *hack_tree; git_reference *branch, *head; git_buf file_path = GIT_BUF_INIT; cl_git_pass(git_repository_index(&index, g_repo)); /* Create a branch pointing at the parent */ cl_git_pass(git_revparse_single(&g_object, g_repo, parent_sha)); cl_git_pass(git_branch_create(&branch, g_repo, "potential_conflict", (git_commit *)g_object, 0)); /* Make HEAD point to this branch */ cl_git_pass(git_reference_symbolic_create( &head, g_repo, "HEAD", git_reference_name(branch), 1, NULL)); git_reference_free(head); git_reference_free(branch); /* Checkout the parent */ g_opts.checkout_strategy = GIT_CHECKOUT_FORCE; cl_git_pass(git_checkout_tree(g_repo, g_object, &g_opts)); /* Hack-ishy workaound to ensure *all* the index entries * match the content of the tree */ cl_git_pass(git_object_peel(&hack_tree, g_object, GIT_OBJ_TREE)); cl_git_pass(git_index_read_tree(index, (git_tree *)hack_tree)); git_object_free(hack_tree); git_object_free(g_object); g_object = NULL; /* Create a conflicting file */ cl_git_pass(git_buf_joinpath(&file_path, "./testrepo", entry_path)); cl_git_mkfile(git_buf_cstr(&file_path), new_content); git_buf_free(&file_path); /* Trying to checkout the original commit */ cl_git_pass(git_revparse_single(&g_object, g_repo, commit_sha)); g_opts.checkout_strategy = GIT_CHECKOUT_SAFE; cl_assert_equal_i( GIT_ECONFLICT, git_checkout_tree(g_repo, g_object, &g_opts)); /* Stage the conflicting change */ cl_git_pass(git_index_add_bypath(index, entry_path)); cl_git_pass(git_index_write(index)); git_index_free(index); cl_assert_equal_i( GIT_ECONFLICT, git_checkout_tree(g_repo, g_object, &g_opts)); }
void test_refs_branches_create__cannot_force_create_over_current_branch(void) { const git_oid *oid; git_reference *branch2; retrieve_known_commit(&target, repo); cl_git_pass(git_branch_lookup(&branch2, repo, "master", GIT_BRANCH_LOCAL)); cl_assert_equal_s("refs/heads/master", git_reference_name(branch2)); cl_assert_equal_i(true, git_branch_is_head(branch2)); oid = git_reference_target(branch2); cl_git_fail_with(-1, git_branch_create(&branch, repo, "master", target, 1, NULL, NULL)); branch = NULL; cl_git_pass(git_branch_lookup(&branch, repo, "master", GIT_BRANCH_LOCAL)); cl_assert_equal_s("refs/heads/master", git_reference_name(branch)); cl_git_pass(git_oid_cmp(git_reference_target(branch), oid)); git_reference_free(branch2); }
void test_network_remote_rename__symref_head(void) { int error; git_reference *ref; git_branch_t btype; git_branch_iterator *iter; git_strarray problems = {0}; char idstr[GIT_OID_HEXSZ + 1] = {0}; git_vector refs; cl_git_pass(git_reference_symbolic_create(&ref, _repo, "refs/remotes/test/HEAD", "refs/remotes/test/master", 0, NULL, NULL)); git_reference_free(ref); cl_git_pass(git_remote_rename(&problems, _repo, _remote_name, "renamed")); cl_assert_equal_i(0, problems.count); git_strarray_free(&problems); cl_git_pass(git_vector_init(&refs, 2, (git_vector_cmp) git_reference_cmp)); cl_git_pass(git_branch_iterator_new(&iter, _repo, GIT_BRANCH_REMOTE)); while ((error = git_branch_next(&ref, &btype, iter)) == 0) { cl_git_pass(git_vector_insert(&refs, ref)); } cl_assert_equal_i(GIT_ITEROVER, error); git_vector_sort(&refs); cl_assert_equal_i(2, refs.length); ref = git_vector_get(&refs, 0); cl_assert_equal_s("refs/remotes/renamed/HEAD", git_reference_name(ref)); cl_assert_equal_s("refs/remotes/renamed/master", git_reference_symbolic_target(ref)); git_reference_free(ref); ref = git_vector_get(&refs, 1); cl_assert_equal_s("refs/remotes/renamed/master", git_reference_name(ref)); git_oid_fmt(idstr, git_reference_target(ref)); cl_assert_equal_s("be3563ae3f795b2b4353bcce3a527ad0a4f7f644", idstr); git_reference_free(ref); git_vector_free(&refs); cl_git_fail_with(GIT_ITEROVER, git_branch_next(&ref, &btype, iter)); git_branch_iterator_free(iter); }
/* * call-seq: * reference.log? -> true or false * * Return +true+ if the reference has a reflog, +false+ otherwise. */ static VALUE rb_git_has_reflog(VALUE self) { git_reference *ref; git_repository *repo; Data_Get_Struct(self, git_reference, ref); repo = git_reference_owner(ref); return git_reference_has_log(repo, git_reference_name(ref)) ? Qtrue : Qfalse; }
void test_clone_nonetwork__can_checkout_given_branch(void) { g_options.checkout_branch = "test"; cl_git_pass(git_clone(&g_repo, cl_git_fixture_url("testrepo.git"), "./foo", &g_options)); cl_assert_equal_i(0, git_repository_head_unborn(g_repo)); cl_git_pass(git_repository_head(&g_ref, g_repo)); cl_assert_equal_s(git_reference_name(g_ref), "refs/heads/test"); }