public inbox for git@vger.kernel.org 
 help / color / mirror / Atom feed
From: Shreyansh Paliwal <shreyanshpaliwalcmsmn@gmail•com>
To: git@vger•kernel.org
Cc: gitster@pobox•com, Shreyansh Paliwal <shreyanshpaliwalcmsmn@gmail•com>
Subject: [PATCH 1/3] show-index: implement automatic hash detection
Date: Tue, 20 Jan 2026 19:35:39 +0530	[thread overview]
Message-ID: <20260120140901.517928-2-shreyanshpaliwalcmsmn@gmail.com> (raw)
In-Reply-To: <20260120140901.517928-1-shreyanshpaliwalcmsmn@gmail.com>

When git show-index is run outside a repository,
it currently falls back to SHA-1 unless the hash algorithm
is explicitly specified via --object-format.
This can lead to failures when reading SHA-256 pack index files.

To prevent this add an automatic hash algorithm detection,
as suggested by an existing TODO comment in the code.

For v2 index files, the fixed size can be computed and then,
the overall file size combined with the number of objects,
can be used to compute the hash size of the objects.
Since SHA-1 and SHA-256 use fixed hash sizes (20 and 32 bytes,
respectively), the hash algorithm can be determined.

This detection is limited in scope. It only applies when the
index file does not contain any 64-bit offset entries, which introduce
additional variable-sized data into the file layout. When such offsets are
present, automatic detection becomes irrelevant, and the user is instead
required to specify the hash algorithm explicitly using --object-format.

Signed-off-by: Shreyansh Paliwal <shreyanshpaliwalcmsmn@gmail•com>
---
 builtin/show-index.c | 45 +++++++++++++++++++++++++++++++++-----------
 1 file changed, 34 insertions(+), 11 deletions(-)

diff --git a/builtin/show-index.c b/builtin/show-index.c
index 2c3e2940ce..be62edc57b 100644
--- a/builtin/show-index.c
+++ b/builtin/show-index.c
@@ -40,17 +40,6 @@ int cmd_show_index(int argc,
 		repo_set_hash_algo(the_repository, hash_algo);
 	}
 
-	/*
-	 * Fallback to SHA1 if we are running outside of a repository.
-	 *
-	 * TODO: Figure out and implement a way to detect the hash algorithm in use by the
-	 *       the index file passed in and use that instead.
-	 */
-	if (!the_hash_algo)
-		repo_set_hash_algo(the_repository, GIT_HASH_DEFAULT);
-
-	hashsz = the_hash_algo->rawsz;
-
 	if (fread(top_index, 2 * 4, 1, stdin) != 1)
 		die("unable to read header");
 	if (top_index[0] == htonl(PACK_IDX_SIGNATURE)) {
@@ -71,6 +60,40 @@ int cmd_show_index(int argc,
 			die("corrupt index file");
 		nr = n;
 	}
+
+	/* detection of hash algorithm
+	Only works for small files, i.e without large offsets */
+	if(!the_hash_algo && version == 2) {
+		struct stat st;
+		size_t file_base_size;
+		size_t table_size;
+		size_t size_rem;
+		size_t hash_size;
+
+		if(fstat(0, &st) || !S_ISREG(st.st_mode))
+			die(_("unable to detect hash from non-regular file"));
+		
+		file_base_size = 8 + (256 * 4);
+		table_size = file_base_size + (nr * 4 * 4);
+		size_rem = st.st_size - table_size;
+		hash_size = size_rem / (nr + 2);
+
+		if(hash_size == GIT_SHA1_RAWSZ) {
+			repo_set_hash_algo(the_repository, GIT_HASH_SHA1);
+		} else if(hash_size == GIT_SHA256_RAWSZ) {
+			repo_set_hash_algo(the_repository, GIT_HASH_SHA256);
+		} else {
+			die(_("unable to detect hash algorithm, "
+					"use --object-format option"));
+		}
+	}
+
+	/* Final fallback to SHA1 */
+	if(!the_hash_algo)
+		repo_set_hash_algo(the_repository, GIT_HASH_SHA1);
+
+	hashsz = the_hash_algo->rawsz;
+
 	if (version == 1) {
 		for (i = 0; i < nr; i++) {
 			unsigned int offset, entry[(GIT_MAX_RAWSZ + 4) / sizeof(unsigned int)];
-- 
2.52.0

  reply	other threads:[~2026-01-20 14:09 UTC|newest]

Thread overview: 25+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-01-20 14:05 [RFC][PATCH 0/3] show-index: modernize and implement auto-detection of hash algorithm Shreyansh Paliwal
2026-01-20 14:05 ` Shreyansh Paliwal [this message]
2026-01-20 18:07   ` [PATCH 1/3] show-index: implement automatic hash detection Junio C Hamano
2026-01-21  8:09     ` Patrick Steinhardt
2026-01-21 10:31       ` Shreyansh Paliwal
2026-01-23  7:22         ` Patrick Steinhardt
2026-01-23 16:08           ` Shreyansh Paliwal
2026-01-23 20:29       ` brian m. carlson
2026-01-21 10:28     ` Shreyansh Paliwal
2026-01-20 14:05 ` [PATCH 2/3] show-index: use gettext wrapping in error messages Shreyansh Paliwal
2026-01-20 14:05 ` [PATCH 3/3] show-index: remove global state variables Shreyansh Paliwal
2026-01-21 10:39   ` Phillip Wood
2026-01-21 12:47     ` Shreyansh Paliwal
2026-01-21 17:23     ` Junio C Hamano
2026-01-29 15:36 ` [PATCH] show-index: warn when falling back to SHA-1 outside a repository Shreyansh Paliwal
2026-01-29 23:03   ` Junio C Hamano
2026-01-30  8:59     ` Shreyansh Paliwal
2026-01-29 23:12   ` brian m. carlson
2026-01-30  9:04     ` Shreyansh Paliwal
2026-01-30 13:40       ` Patrick Steinhardt
2026-01-30 17:01         ` Junio C Hamano
2026-01-30 15:31   ` [PATCH V2 0/2] show-index: add warning and wrap error messages with gettext Shreyansh Paliwal
2026-01-30 15:31     ` [PATCH V2 1/2] show-index: warn when falling back to SHA-1 outside a repository Shreyansh Paliwal
2026-01-30 15:31     ` [PATCH V2 2/2] show-index: use gettext wrapping in user facing error messages Shreyansh Paliwal
2026-01-30 17:07     ` [PATCH V2 0/2] show-index: add warning and wrap error messages with gettext Junio C Hamano

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20260120140901.517928-2-shreyanshpaliwalcmsmn@gmail.com \
    --to=shreyanshpaliwalcmsmn@gmail$(echo .)com \
    --cc=git@vger$(echo .)kernel.org \
    --cc=gitster@pobox$(echo .)com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox