aboutsummaryrefslogtreecommitdiffstats
path: root/refs.h
diff options
context:
space:
mode:
authorJunio C Hamano <gitster@pobox.com>2025-11-03 07:27:58 -0800
committerJunio C Hamano <gitster@pobox.com>2025-11-03 07:27:58 -0800
commit8ac48a10de61267858d66383c34833e55a5e9d02 (patch)
treec944ea41f08960307abbd4c2c4e558e898e20c4c /refs.h
parentMerge branch 'tc/last-modified-active-paths-optimization' into next (diff)
parentref-filter: parse objects on demand (diff)
downloadgit-8ac48a10de61267858d66383c34833e55a5e9d02.tar.gz
git-8ac48a10de61267858d66383c34833e55a5e9d02.zip
Merge branch 'ps/ref-peeled-tags' into next
Some ref backend storage can hold not just the object name of an annotated tag, but the object name of the object the tag points at. The code to handle this information has been streamlined. * ps/ref-peeled-tags: ref-filter: parse objects on demand ref-filter: detect broken tags when dereferencing them refs: don't store peeled object IDs for invalid tags object: add flag to `peel_object()` to verify object type refs: drop infrastructure to peel via iterators refs: drop `current_ref_iter` hack builtin/show-ref: convert to use `reference_get_peeled_oid()` ref-filter: propagate peeled object ID upload-pack: convert to use `reference_get_peeled_oid()` refs: expose peeled object ID via the iterator refs: refactor reference status flags refs: fully reset `struct ref_iterator::ref` on iteration refs: introduce `.ref` field for the base iterator refs: introduce wrapper struct for `each_ref_fn`
Diffstat (limited to 'refs.h')
-rw-r--r--refs.h88
1 files changed, 56 insertions, 32 deletions
diff --git a/refs.h b/refs.h
index 4e6bd63aa8..2dd7ac1a16 100644
--- a/refs.h
+++ b/refs.h
@@ -333,36 +333,74 @@ struct ref_transaction;
* stored in ref_iterator::flags. Other bits are for internal use
* only:
*/
+enum reference_status {
+ /* Reference is a symbolic reference. */
+ REF_ISSYMREF = (1 << 0),
-/* Reference is a symbolic reference. */
-#define REF_ISSYMREF 0x01
+ /* Reference is a packed reference. */
+ REF_ISPACKED = (1 << 1),
-/* Reference is a packed reference. */
-#define REF_ISPACKED 0x02
+ /*
+ * Reference cannot be resolved to an object name: dangling symbolic
+ * reference (directly or indirectly), corrupt reference file,
+ * reference exists but name is bad, or symbolic reference refers to
+ * ill-formatted reference name.
+ */
+ REF_ISBROKEN = (1 << 2),
-/*
- * Reference cannot be resolved to an object name: dangling symbolic
- * reference (directly or indirectly), corrupt reference file,
- * reference exists but name is bad, or symbolic reference refers to
- * ill-formatted reference name.
- */
-#define REF_ISBROKEN 0x04
+ /*
+ * Reference name is not well formed.
+ *
+ * See git-check-ref-format(1) for the definition of well formed ref names.
+ */
+ REF_BAD_NAME = (1 << 3),
+};
+
+/* A reference passed to `for_each_ref()`-style callbacks. */
+struct reference {
+ /* The fully-qualified name of the reference. */
+ const char *name;
+
+ /* The target of a symbolic ref. `NULL` for direct references. */
+ const char *target;
+
+ /*
+ * The object ID of a reference. Either the direct object ID or the
+ * resolved object ID in the case of a symbolic ref. May be the zero
+ * object ID in case the symbolic ref cannot be resolved.
+ */
+ const struct object_id *oid;
+
+ /*
+ * An optional peeled object ID. This field _may_ be set for tags in
+ * case the peeled value is present in the backend. Please refer to
+ * `reference_get_peeled_oid()`.
+ */
+ const struct object_id *peeled_oid;
+
+ /* A bitfield of `enum reference_status` flags. */
+ unsigned flags;
+};
/*
- * Reference name is not well formed.
+ * Peel the tag to a non-tag commit. If present, this uses the peeled object ID
+ * exposed by the reference backend. Otherwise, the object is peeled via the
+ * object database, which is less efficient.
*
- * See git-check-ref-format(1) for the definition of well formed ref names.
+ * Return `0` if the reference could be peeled, a negative error code
+ * otherwise.
*/
-#define REF_BAD_NAME 0x08
+int reference_get_peeled_oid(struct repository *repo,
+ const struct reference *ref,
+ struct object_id *peeled_oid);
/*
* The signature for the callback function for the for_each_*()
- * functions below. The memory pointed to by the refname and oid
- * arguments is only guaranteed to be valid for the duration of a
+ * functions below. The memory pointed to by the `struct reference`
+ * argument is only guaranteed to be valid for the duration of a
* single callback invocation.
*/
-typedef int each_ref_fn(const char *refname, const char *referent,
- const struct object_id *oid, int flags, void *cb_data);
+typedef int each_ref_fn(const struct reference *ref, void *cb_data);
/*
* The following functions invoke the specified callback function for
@@ -1251,10 +1289,6 @@ int repo_migrate_ref_storage_format(struct repository *repo,
* to the next entry, ref_iterator_advance() aborts the iteration,
* frees the ref_iterator, and returns ITER_ERROR.
*
- * The reference currently being looked at can be peeled by calling
- * ref_iterator_peel(). This function is often faster than peel_ref(),
- * so it should be preferred when iterating over references.
- *
* Putting it all together, a typical iteration looks like this:
*
* int ok;
@@ -1269,9 +1303,6 @@ int repo_migrate_ref_storage_format(struct repository *repo,
* // Access information about the current reference:
* if (!(iter->flags & REF_ISSYMREF))
* printf("%s is %s\n", iter->refname, oid_to_hex(iter->oid));
- *
- * // If you need to peel the reference:
- * ref_iterator_peel(iter, &oid);
* }
*
* if (ok != ITER_DONE)
@@ -1362,13 +1393,6 @@ enum ref_iterator_seek_flag {
int ref_iterator_seek(struct ref_iterator *ref_iterator, const char *refname,
unsigned int flags);
-/*
- * If possible, peel the reference currently being viewed by the
- * iterator. Return 0 on success.
- */
-int ref_iterator_peel(struct ref_iterator *ref_iterator,
- struct object_id *peeled);
-
/* Free the reference iterator and any associated resources. */
void ref_iterator_free(struct ref_iterator *ref_iterator);