Commit Graph

81648 Commits (4e60bb0027ecddc045af55e20b59950e31dbd0c4)

Author SHA1 Message Date
Junio C Hamano 4e60bb0027 Merge branch 'kk/reftable-tombstone-quadratic-fix' into next
The performance of ref updates and reads using the 'reftable' backend
in the presence of many deletion tombstone records has been optimized
by removing the tombstone suppression flag from the merged iterator
and instead skipping tombstones at higher-level call sites where
iteration bounds are known.

* kk/reftable-tombstone-quadratic-fix:
  reftable: fix quadratic behavior in the presence of tombstones
  t/perf: add perf test for ref tombstone scenarios
2026-07-12 11:14:32 -07:00
Junio C Hamano 295a5f9b34 Merge branch 'kk/commit-graph-topo-levels-fix' into next
The 'topo_levels' slab was propagated only to the topmost layer of a
split commit-graph chain, causing incremental writes to recompute
topological levels for commits in base layers. This has been
corrected.

* kk/commit-graph-topo-levels-fix:
  commit-graph: propagate topo_levels slab to all chain layers
  commit-graph: add trace2 instrumentation for generation DFS
2026-07-12 11:14:32 -07:00
Junio C Hamano 39e9fdb93f Merge branch 'ty/migrate-ignorecase' into next
The global configuration variable 'ignore_case' (representing the
'core.ignorecase' configuration) has been migrated into 'struct
repo_config_values' to tie it to a specific repository instance.

* ty/migrate-ignorecase:
  config: use repo_ignore_case() to access core.ignorecase
  environment: move ignore_case into repo_config_values
2026-07-12 11:14:31 -07:00
Junio C Hamano 9da32fdaf7 Merge branch 'tc/bundle-uri-empty-fix' into next
The client-side parser of server-advertised bundle-URI list has been
updated to drain the remaining response in order to avoid protocol
desynchronization when the server sends a misconfigured list. Also,
the server-side has been taught to omit empty configuration values
instead of sending invalid key-value lines.

* tc/bundle-uri-empty-fix:
  bundle-uri: stop sending invalid bundle configuration
  bundle-uri: drain remaining response on invalid bundle-uri lines
2026-07-12 11:14:31 -07:00
Junio C Hamano 744f1aede4 Merge branch 'hf/unpack-trees-quadratic-scan' into next
The cache-scanning loop in 'next_cache_entry()' has been optimized
to avoid rescanning already-unpacked index entries, preventing a
quadratic performance slow-down when diffing the working tree
against a commit with a pathspec matching early index entries.

* hf/unpack-trees-quadratic-scan:
  unpack-trees: avoid quadratic index scan in next_cache_entry()
2026-07-12 11:14:31 -07:00
Junio C Hamano adeaa999b6 Merge branch 'wy/doc-myfirstcontribution-trim-quotes' into next
The contributor guide has been updated to advise new contributors to
trim irrelevant quoted text when replying to review comments, matching
the existing advice given to reviewers.

* wy/doc-myfirstcontribution-trim-quotes:
  MyFirstContribution: mention trimming quoted text in replies
2026-07-12 11:14:31 -07:00
Junio C Hamano d0cf55ea54 Merge branch 'gr/t1410-reflog-exit-code' into next
The pipelines in 't1410-reflog.sh' have been replaced with the
'test_stdout_line_count' helper to avoid suppressing the exit code of
'git' commands, ensuring failures are not hidden from the test suite.

* gr/t1410-reflog-exit-code:
  t1410-reflog.sh: avoid suppressing git's exit code in pipelines
2026-07-10 08:27:02 -07:00
Junio C Hamano 1916c07bf5 Merge branch 'mm/test-grep-lint' into next
The test suite has been updated to use the 'test_grep' helper instead
of bare 'grep' for test assertions, allowing file contents to be
printed on failure for easier debugging. A new 'greplint' linter has
been introduced to detect and prevent new bare 'grep' assertions from
being added to the test suite.

* mm/test-grep-lint:
  t: add greplint to detect bare grep assertions
  t: convert grep assertions to test_grep
  t: fix Lexer line count for $() inside double-quoted strings
  t: extract chainlint's parser into shared module
  t: fix grep assertions missing file arguments
  t/README: document test_grep helper
2026-07-10 08:27:02 -07:00
Junio C Hamano fe82b5d188 Merge branch 'sn/osxkeychain-rust-universal' into next
The build system has been updated to support building universal macOS
binaries when 'Rust' is enabled, by compiling separate static archives
for each target triple listed in 'RUST_TARGETS' and combining them
using the macOS 'lipo' tool. The 'git-credential-osxkeychain' helper
has been updated to link against '$(RUST_LIB)' when 'Rust' is enabled.

* sn/osxkeychain-rust-universal:
  contrib: wire up osxkeychain in contrib/Makefile on macOS
  Makefile: support universal macOS builds via RUST_TARGETS
  Makefile: add $(RUST_LIB) prerequisite to osxkeychain
2026-07-10 08:27:01 -07:00
Junio C Hamano 775654e447 Merge branch 'bc/parse-options-exit-0-on-help' into next
Option parsing with 'git rev-parse --parseopt' and in most 'git'
subcommands has been updated to exit with 0 (instead of 129) when the
help option ('-h' or '--help') is requested directly by the user,
aligning with standard Unix convention.

* bc/parse-options-exit-0-on-help:
  parse-options: exit 0 on -h
  rev-parse: have --parseopt callers exit 0 on --help
  parse-options: add a separate case for help output on error
  t1517: skip svn tests if svn is not installed
2026-07-10 08:27:00 -07:00
Junio C Hamano 41b9b65b23 Merge branch 'jc/submitting-patches-abandoning' into next
The 'SubmittingPatches' document has been updated to explicitly
describe the expectation for contributors to retract or abandon their
patch series when they are no longer pursuing it.

* jc/submitting-patches-abandoning:
  SubmittingPatches: document how to retract a topic
2026-07-10 08:27:00 -07:00
Junio C Hamano 0444c74d81 Merge branch 'kk/commit-reach-find-all-fix' into next
The early-exit optimization in 'paint_down_to_common()' has been gated
on the queue being generation-ordered, fixing a bug where 'git merge-
base' (without '--all') could return incorrect results on repositories
with v1 commit graphs and clock skew.

* kk/commit-reach-find-all-fix:
  commit-reach: guard !FIND_ALL early exit with generation ordering check
  t6600: add test for merge-base early exit with clock skew
2026-07-10 08:27:00 -07:00
Junio C Hamano 444d202a75 Merge branch 'jc/relnotes-2.55-rust-fix' into next
A description in the release notes for Git 2.55.0 has been
retroactively updated to clarify that Rust support is enabled by
default, but still optional, and will become mandatory in Git 3.0.

* jc/relnotes-2.55-rust-fix:
  Rust: fix description in Release Notes to 2.55
2026-07-10 08:26:59 -07:00
Junio C Hamano 1691a942ab Merge branch 'ps/setup-split-discovery-and-setup' into next
The repository discovery and repository configuration phases, which
were previously intertwined in 'setup.c', have been split. Repository
discovery has been updated to populate a 'struct repo_discovery'
without modifying the repository state, which is then taken by
repository configuration to initialize the repository, paving the way
for clean unification of repository configuration.

* ps/setup-split-discovery-and-setup:
  setup: mark `set_git_work_tree()` as file-local
  setup: pass worktree to `init_db()`
  setup: drop redundant configuration of `startup_info->have_repository`
  setup: make repository discovery self-contained
  setup: propagate prefix via repository discovery
  setup: drop static `cwd` variable
  setup: move prefix into repository
  setup: embed repository format in discovery
  setup: introduce explicit repository discovery
  setup: split up concerns of `setup_git_env_internal()`
  setup: unify setup of shallow file
  setup: mark bogus worktree in `apply_repository_format()`
  setup: rename `check_repository_format_gently()`
2026-07-10 08:26:59 -07:00
Junio C Hamano b8f4dd0ab9 Merge branch 'ps/reftable-hardening' into next
The reftable code has been hardened against corrupted tables by
fixing out-of-bounds writes, out-of-bounds reads, and abort calls
during parsing.

* ps/reftable-hardening:
  reftable/table: fix OOB read on truncated table
  reftable/table: fix NULL pointer access when seeking to bogus offsets
  reftable/block: fix OOB read with bogus restart offset
  reftable/block: fix use of uninitialized memory when binsearch fails
  reftable/block: fix OOB read with bogus restart count
  reftable/block: fix OOB read with bogus block size
  reftable/block: fix OOB write with bogus inflated log size
  t/unit-tests: introduce test helper to write reftable blocks
  reftable/record: don't abort when decoding invalid ref value type
  reftable/basics: fix OOB read on binary search of empty range
  oss-fuzz: add fuzzer for parsing reftables
  meson: support building fuzzers with libFuzzer
2026-07-10 08:26:59 -07:00
Kristofer Karlsson 146a946321 reftable: fix quadratic behavior in the presence of tombstones
When many tombstones are present in a reftable, operations that need
to look up or iterate over refs exhibit quadratic behavior.  With
8000 refs deleted and re-created, update-ref takes ~15s, quadrupling
for each doubling of input size.

The root cause is the merged iterator's suppress_deletions flag.
When set, merged_iter_next_void() silently consumes tombstone records
in a tight internal loop before returning to the caller.  This
prevents higher-level code from checking iteration bounds (such as
prefix or refname comparisons) until after all tombstones have been
scanned.

This affects any code path that seeks into a range containing
tombstones, including:

 - refs_verify_refnames_available() seeks to "refs/tags/foo-1/" to
   check for D/F conflicts and must scan through all subsequent
   tombstones before the caller can see that they are past the prefix
   of interest.

 - reftable_backend_read_ref() seeks to a specific refname and must
   scan through all subsequent tombstones before returning "not
   found", because the merged iterator skips the matching tombstone
   and searches for the next live record.

Fix this by making suppress_deletions configurable via
reftable_stack_options instead of unconditionally enabling it.  Git
no longer sets the flag, so tombstones are now returned to callers in
the reftable backend, which skip them after their existing bounds
checks.  This allows iteration to terminate as soon as a tombstone
past the relevant bound is encountered.

Downstream users of the reftable library (e.g. libgit2) can still
enable suppress_deletions through the stack options to retain the
previous behavior.

This also requires adding deletion checks to the log iteration paths,
since suppress_deletions applied to both ref and log iterators.

Both tests in p1401 go from ~13s to ~0.2s with this change.

Reported-by: Jeff King <peff@peff.net>
Signed-off-by: Kristofer Karlsson <krka@spotify.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-10 08:18:56 -07:00
Kristofer Karlsson 13d8160f49 t/perf: add perf test for ref tombstone scenarios
Add performance tests for update-ref when many tombstones are present
in a reftable.

The first test exercises the scenario where all refs are deleted
(creating tombstones) and then re-created with the same names, which
currently exhibits quadratic behavior.

The second test uses a separate repository with an asymmetric variant
where refs are deleted and then new, differently-named refs are
created.  When the tombstones sort after the new refs, every create
scans all tombstones, making this case even worse than re-creating
the same refs.

Helped-by: Jeff King <peff@peff.net>
Signed-off-by: Kristofer Karlsson <krka@spotify.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-10 08:18:56 -07:00
Junio C Hamano 6434b31f56 Sync with 'master' 2026-07-09 11:05:52 -07:00
Kristofer Karlsson 8ea36f63d8 commit-graph: propagate topo_levels slab to all chain layers
The topo_levels slab is only propagated to the topmost graph
layer instead of all layers in the chain.  Commits from lower
layers appear to have no generation numbers, so the DFS
re-walks the entire ancestry.

Fix by making topo_levels visible to all layers, not just
the first one.

Signed-off-by: Kristofer Karlsson <krka@spotify.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-09 10:29:23 -07:00
Kristofer Karlsson 02d62c33be commit-graph: add trace2 instrumentation for generation DFS
Count the number of steps taken in
compute_reachable_generation_numbers() and expose it via
trace2 to make it easier to detect performance regressions.

Add a failing test for such a regression, introduced in
199d452758 (commit-graph: return the prepared commit graph
from `prepare_commit_graph()`, 2025-09-04), where incremental
commit-graph writes do not see existing generation numbers
from lower graph layers and fall back to walking the full
ancestry.

Signed-off-by: Kristofer Karlsson <krka@spotify.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-09 10:29:23 -07:00
Taylor Blau f60db8d575 mailmap: map Taylor Blau's work address
Signed-off-by: Taylor Blau <ttaylorr@openai.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-09 09:43:23 -07:00
Gatla Vishweshwar Reddy c4fcd5039b t1410-reflog.sh: avoid suppressing git's exit code in pipelines
Piping git commands directly to wc -l suppresses the exit code of
git, hiding potential failures from the test suite. Use
test_stdout_line_count instead, which handles exit code preservation
internally while keeping the test logic clean and readable.

Signed-off-by: Gatla Vishweshwar Reddy <gatlavishweshwarreddy26@gmail.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-09 09:36:19 -07:00
Junio C Hamano 371c2e9c3b Merge branch 'tc/replay-linearize' into next
The 'git replay' command has been taught the '--linearize' option to
drop merge commits and linearize the replayed history, mimicking 'git
rebase --no-rebase-merges'.

* tc/replay-linearize:
  replay: offer an option to linearize the commit topology
  replay: resolve the replay base outside pick_regular_commit()
  replay: add helper to put entry into replayed_commits
2026-07-09 07:45:16 -07:00
Junio C Hamano fd2b979b73 Merge branch 'mm/sideband-ansi-sgr-colon-fix' into next
The sideband demultiplexer has been updated to recognize ANSI SGR
escape sequences that use colon-separated subfields (e.g., for
256-color or true-color codes).

* mm/sideband-ansi-sgr-colon-fix:
  sideband: allow ANSI SGR with colon-separated subfields
2026-07-09 07:45:15 -07:00
Junio C Hamano 12a4856545 Merge branch 'jk/git-hash-cleanups' into next
The 'git_hash_*()' wrappers have been updated to be used consistently
across the codebase instead of direct calls to members of 'struct
git_hash_algo', and 'git_hash_discard()' has been made idempotent to
simplify cleanups.

* jk/git-hash-cleanups:
  hash: check ctx->active flag in all wrapper functions
  http: use idempotent git_hash_discard()
  csum-file: use idempotent git_hash_discard()
  hash: make git_hash_discard() idempotent
  hash: document function pointers and wrappers
  hash: convert remaining direct function calls
  hash: use git_hash_init() consistently
2026-07-09 07:45:15 -07:00
Junio C Hamano 737a87f65e Merge branch 'ih/precompose-flex-array' into next
The UTF-8 precomposition wrapper on macOS has been updated to use a
flexible array member to represent the name of a directory entry,
preventing fortified libc checks from failing when the name is
reallocated to be larger than 'NAME_MAX' bytes.

* ih/precompose-flex-array:
  precompose_utf8: use a flex array for d_name
2026-07-09 07:45:15 -07:00
Junio C Hamano c5b13248c8 Merge branch 'ps/t-fixes-for-git-test-long' into next
Various test scripts have been updated to clean up large temporary
files and repositories, reducing peak disk usage during testing.
Also, expensive tests have been disabled on platforms that lack
sufficient resources (like 32-bit platforms and Windows CI
runners), and the long test suite has been enabled in GitLab CI.

* ps/t-fixes-for-git-test-long:
  gitlab-ci: enable "GIT_TEST_LONG"
  gitlab-ci: disable RAM disk on macOS jobs
  t: use `test_bool_env` to parse GIT_TEST_LONG
  t7900: clean up large EXPENSIVE repository
  t7508: skip EXPENSIVE test that is broken without SIZE_T_IS_64BIT
  t5608: reduce maximum disk usage
  t4141: fix inefficient use of dd(1)
  t0021: skip EXPENSIVE test that is broken without SIZE_T_IS_64BIT
  README: add GitLab CI badge to make it more discoverable
2026-07-09 07:45:14 -07:00
Junio C Hamano cd80e673a5 Merge branch 'js/ci-dockerized-pid-limit' into next
Dockerized CI jobs running in private GitHub repositories have been
adjusted to use explicit process and file limits, preventing resource
exhaustion errors on private runners.

* js/ci-dockerized-pid-limit:
  ci(dockerized): raise the PID limit for private repositories
2026-07-09 07:45:14 -07:00
Junio C Hamano 1823fe297c Merge branch 'js/coverity-fixes' into next
Various resource leaks, invalid file descriptor closures, and process
handle ownership issues flagged by Coverity have been fixed.

* js/coverity-fixes:
  mingw: make `exit_process()` own the process handle on all paths
  fsmonitor: plug token-data leak on early daemon-startup failures
  reftable/table: release filter on error path
  imap-send: avoid leaking the IMAP upload buffer
  worktree: fix resource leaks when branch creation fails
  submodule: fix cwd leak in `get_superproject_working_tree()`
  dir: free allocations on parse-error paths in `read_one_dir()`
  line-log: avoid redundant copy that leaks in process_ranges
  run-command: avoid `close(-1)` in `start_command()` error paths
  download_https_uri_to_file(): do not leak fd upon failure
  loose: avoid closing invalid fd on error path
  load_one_loose_object_map(): fix resource leak
2026-07-09 07:45:14 -07:00
Junio C Hamano 7db7b74972 Merge branch 'jk/hash-algo-leak-fixes' into next
Various code paths that initialize a cryptographic hash context but
bail out or finish without calling 'git_hash_final()' have been taught
to call 'git_hash_discard()' to release allocated resources, fixing
memory leaks when Git is built with non-default backends like
'OpenSSL' or 'libgcrypt'.

* jk/hash-algo-leak-fixes:
  hash: add platform-specific discard functions
  hash: fix memory leak copying sha256 gcrypt handles
  http: discard hash in dumb-http http_object_request
  check_stream_oid(): discard hash on read error
  patch-id: discard hash when done
  csum-file: provide a function to release checkpoints
  csum-file: always finalize or discard hash
  hash: add discard primitive
  csum-file: drop discard_hashfile()
2026-07-09 07:45:14 -07:00
Henrique Ferreiro 716766765c unpack-trees: avoid quadratic index scan in next_cache_entry()
Diffing the working tree against a commit with a pathspec can take
time quadratic in the size of the index when the pathspec matches a
subtree whose entries are the first entries of the index.  Fix it by
having next_cache_entry() record how far it scanned in cache_bottom,
so repeated calls no longer rescan the growing prefix of
already-unpacked entries.  On a Chromium checkout (~500k index
entries),

	git diff HEAD -- .agents/OWNERS

took about 8 minutes before this change and 0.07 seconds after it.
The same diff without the commit, without the pathspec, or with
--cached was already instant.

Add p0009-diff-pathspec.sh, which builds a 10,000-entry index whose
first path lives in a subtree (100,000 entries under --long-tests),
to guard against the regression.  Comparing v2.55.0 with this change
using GIT_TEST_LONG=t:

Test                            v2.55.0           HEAD
------------------------------------------------------------------------
0009.2: diff pathspec subtree   7.16(7.12+0.01)   0.02(0.01+0.00) -99.7%

Signed-off-by: Henrique Ferreiro <hferreiro@igalia.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-08 14:54:21 -07:00
Justin Tobler 50de1169e4 bundle-uri: stop sending invalid bundle configuration
When bundle-URI info is requested by the client, the server responds
with all "bundle.*" config lines as key=value packet lines. On the
client-side, the received bundle config packet lines are always expected
to contain both a key and a value otherwise the client errors out during
parsing. The server performs no validation of the read bundle
configuration though which results in any misconfiguration on the
server-side, such as bundle configuration with an empty value, being
blindly sent to the client.

To avoid having the server transmit invalid configuration to clients,
only send bundle configuration that has non-empty values.

This change makes bundle-URI information sent by the server
syntactically correct, but semantically it still can be invalid. For
example the server may end up sending `bundle.bundle-1.creationToken`,
but be lacking a `bundle.bundle-1.uri` for that bundle. The `uri` is
mandatory, thus the client cannot process this bundle and will error
with the message:

    error: bundle 'bundle-1' has no uri

Fixing this would require a more complex solution, because bundles need
to be validated as a whole and not line-by-line. This is considered
outside the scope of this change.

Co-authored-by: Toon Claes <toon@iotcl.com>
Signed-off-by: Justin Tobler <jltobler@gmail.com>
Signed-off-by: Toon Claes <toon@iotcl.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-08 13:54:16 -07:00
Toon Claes 8585c50b05 bundle-uri: drain remaining response on invalid bundle-uri lines
On clone, when the client sends the `bundle-uri` command, the server
might respond with invalid data. For example if it sends information
about a bundle where the 'uri' is empty, it produces the following
error:

    Cloning into 'foo'...
    error: bundle-uri: line has empty key or value
    error: error on bundle-uri response line 4: bundle.bundle-1.uri=
    error: could not retrieve server-advertised bundle-uri list

This error is bubbled up to `transport_get_remote_bundle_uri()`, which
is called by `cmd_clone()` in builtin/clone.c. Over here, the return
value is ignored, so clone continues.

Despite this, it still dies with this error:

    fatal: expected 'packfile'

This happens because `get_remote_bundle_uri()` exited early, leaving
some unprocessed packet data behind in the read buffer. This is
misleading to the user, because it suggests a problem with the packfile
exchange, when in reality it's caused by a misconfigured bundle-URI on
the server-side.

Fix this by continuing to read packets when an error was encountered,
but without processing the remaining lines. This drains the protocol
stream so no stale data is left behind and the caller can use it if they
like.

With this, clone now continues successfully if invalid bundle-URI data
was sent by the server. This is intentional, because since the inception
of `transport_get_remote_bundle_uri()` in 0cfde740f0 (clone: request the
'bundle-uri' command when available, 2022-12-22) the return value of
that function is ignored in `cmd_clone()` so the clone can continue
without bundles.

Signed-off-by: Toon Claes <toon@iotcl.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-08 13:54:16 -07:00
Junio C Hamano e4962bd3d5 Merge branch 'rs/blame-abbrev-marks' into next
The alignment of commit object name abbreviations in 'git blame'
output has been optimized to reserve a column for marks (caret,
question mark, or asterisk) only when such marks are actually shown.

* rs/blame-abbrev-marks:
  blame: reserve mark column only if necessary
2026-07-08 12:07:01 -07:00
Junio C Hamano 10763a0ebc Merge branch 'mg/meson-hook-list-buildfix' into next
A racy build failure under Meson has been corrected by ensuring that
the generated header file 'hook-list.h' is built before compiling files
in 'builtin_sources' that depend on it.

* mg/meson-hook-list-buildfix:
  meson: restore hook-list.h to builtin_sources
2026-07-08 12:07:01 -07:00
Junio C Hamano 3b9a1cda3f Merge branch 'jk/bloom-leak-fixes' into next
Various memory leaks in the Bloom-filter code paths that are exposed
when running tests with the 'GIT_TEST_COMMIT_GRAPH_CHANGED_PATHS=1'
environment variable have been plugged.

* jk/bloom-leak-fixes:
  line-log: drop extra copy of range with bloom filters
  revision: avoid leaking bloom keyvecs with multiple traversals
  bloom: make bloom-filter slab initialization idempotent
2026-07-08 12:07:01 -07:00
Junio C Hamano 6fb84708a4 Merge branch 'ps/history-drop' into next
The experimental 'git history' command has been taught a new 'drop'
subcommand to remove a commit and replay its descendants onto its
parent.

* ps/history-drop:
  builtin/history: implement "drop" subcommand
  builtin/history: split handling of ref updates into two phases
  replay: expose `replay_result_queue_update()`
  reset: stop assuming that the caller passes in a clean index
  reset: allow the caller to specify the current HEAD object
  reset: introduce ability to skip updating HEAD
  reset: introduce dry-run mode
  reset: modernize flags passed to `reset_working_tree()`
  reset: rename `reset_head()`
  reset: drop `USE_THE_REPOSITORY_VARIABLE`
  read-cache: split out function to drop unmerged entries to stage 0
2026-07-08 12:07:01 -07:00
Junio C Hamano f43ee51cc3 Merge branch 'ps/odb-drop-whence' into next
The 'whence' field in 'struct object_info' has been removed,
refactoring backend-specific object information retrieval into an opt-
in 'struct object_info_source' structure.

* ps/odb-drop-whence:
  odb: document object info fields
  odb: drop `whence` field from object info
  treewide: convert users of `whence` to the new source field
  odb: add `source` field to struct object_info_source
  odb: make backend-specific fields optional
  packfile: thread odb_source_packed through packed_object_info()
2026-07-08 12:07:00 -07:00
Junio C Hamano f001147283 Merge branch 'ps/refs-writing-subcommands' into next
The 'git refs' toolbox has been extended with new 'create', 'delete',
'update', and 'rename' subcommands to create, delete, update, and
rename references, respectively.

* ps/refs-writing-subcommands:
  builtin/refs: add "rename" subcommand
  builtin/refs: add "create" subcommand
  builtin/refs: add "update" subcommand
  builtin/refs: add "delete" subcommand
  builtin/refs: drop `the_repository`
2026-07-08 12:07:00 -07:00
Junio C Hamano e74c698504 SubmittingPatches: document how to retract a topic
While this document outlines an idealized lifecycle where an author
develops a patch, refines it with reviewer feedback, and
successfully merges it into Git, reality is rarely so seamless.

Sometimes, a topic must be abandoned. Doing so explicitly is far
better than leaving it in limbo, especially since topics can always
be resurrected later.

Clearly state that we encourage contributors to retract any topic
that does not pan out.

Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-08 11:49:01 -07:00
Shardul Natu 1a62c1fc8b contrib: wire up osxkeychain in contrib/Makefile on macOS
When running "make test" with TEST_CONTRIB_TOO=yes (which is default in
macOS CI workflows), $(MAKE) -C contrib/ test is invoked. However,
contrib/Makefile only invoked tests for diff-highlight and subtree,
meaning git-credential-osxkeychain was never built or verified during
standard CI test runs.

Add a "test" target to contrib/credential/osxkeychain/Makefile that
depends on building git-credential-osxkeychain. Additionally, wire up
credential/osxkeychain in contrib/Makefile under "all", "test", and
"clean" whenever running on macOS (Darwin).

This ensures that running "make test" or "make all" in contrib on macOS
automatically builds and links git-credential-osxkeychain, preventing
future build or symbol linking regressions from slipping through CI.

Signed-off-by: Shardul Natu <snatu@google.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-07 21:58:55 -07:00
Shardul Natu 924dfced6b Makefile: support universal macOS builds via RUST_TARGETS
On macOS, Universal Binaries contain native executable code for
multiple architectures (such as Intel x86_64 and Apple Silicon arm64)
bundled into a single file. This is standard practice for macOS
distribution and CI packaging (such as internal distribution packages
or tooling like Burrito/Homebrew), allowing a single build artifact
to run natively across all Macs without Rosetta emulation or
maintaining separate packages.

When building Git C code for multiple architectures on macOS, the
Apple toolchain (clang) natively supports universal builds via
CFLAGS/LDFLAGS. When "-arch x86_64 -arch arm64" is passed, clang
automatically compiles and links universal binaries for all C object
files and executables out of the box.

Cargo and rustc, however, do not support multiple "-arch" flags or
emitting universal binaries in a single invocation. Instead, Cargo
requires invoking each target triple independently (e.g., passing
"--target x86_64-apple-darwin" and "--target aarch64-apple-darwin").

To bridge this gap when Rust is enabled:
  1. Allow specifying space-separated target triples in RUST_TARGETS.
  2. Introduce declarative pattern rules (target/%/...) to compile
     each target-specific library slice via Cargo.
  3. On macOS, if multiple targets are specified, use "lipo" (part of
     the mandatory Xcode Command Line Tools) to combine the resulting
     static libraries into target/release/libgitcore.a.

Once $(RUST_LIB) is compiled into a universal static archive, the
standard C linker seamlessly links it with the C object files to
produce universal Git executables.

Signed-off-by: Shardul Natu <snatu@google.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-07 21:58:54 -07:00
Shardul Natu 87bd9bd40e Makefile: add $(RUST_LIB) prerequisite to osxkeychain
When Rust is enabled, the git-credential-osxkeychain helper depends on
Rust symbols compiled into $(RUST_LIB). While commit 522ea8ef7d
("osxkeychain: fix build with Rust") updated the linker command line to
use $(LIBS), it omitted $(RUST_LIB) from the target prerequisite list.
Without this prerequisite, running a parallel build ("make -j") from a
clean working tree can fail because Make does not know to invoke Cargo
to build libgitcore.a before linking git-credential-osxkeychain.

Note that we depend explicitly on $(LIB_FILE) and $(RUST_LIB) rather
than $(GITLIBS). Unlike standard Git builtins and programs like scalar
(which define cmd_main() and rely on common-main.o to supply main()),
git-credential-osxkeychain.c defines its own standalone int main().
If $(GITLIBS) were used, $(filter %.o,$^) in the link recipe would
match both git-credential-osxkeychain.o and common-main.o, causing a
duplicate symbol linking error for _main on macOS.

Additionally, wrap the definitions of $(RUST_LIB) and the "rust" build
target in "ifndef NO_RUST". This ensures that when NO_RUST=1 is
specified, $(RUST_LIB) evaluates to empty, making the Rust dependency a
clean no-op without needing intermediate variables.

Signed-off-by: Shardul Natu <snatu@google.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-07 21:58:54 -07:00
Jeff King 9e396aa553 hash: check ctx->active flag in all wrapper functions
It only makes sense to call git_hash_update(), etc, on a hash context
that has been initialized but not yet finalized or discarded. This is an
unlikely error to make, but it's easy for us to catch it and complain.

It's especially important because it would quietly "work" for many hash
backends (like sha1dc, which is just manipulating some bytes) but would
cause undefined behavior with others (like OpenSSL, which puts the
context onto the heap). Checking the flag lets us catch problems
consistently on every build.

Note that we can't do the same for git_hash_init(). Even though it would
cause a leak to call it twice (without an intervening final/discard),
the point of the function is that the contents of the struct are
undefined before the call. But calling it twice is an even less likely
error to make, so not covering it is OK.

We leave git_hash_discard() alone, as its idempotent behavior is
convenient for callers. We _could_ try to do something similar for
git_hash_final(), allowing:

  git_hash_final(result, &ctx);
  git_hash_final(other_result, &ctx);

but it does not make much sense. After the first final() call we have
thrown away the state, so we cannot produce the same output. We could
come up with some sensible output (the null hash, or the empty hash),
but double-calls like this are more likely a bug, so our best bet is to
complain loudly (whereas the current code produces either nonsense
output or undefined behavior, depending on the backend).

Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-07 21:56:00 -07:00
Jeff King f1bf9772f8 http: use idempotent git_hash_discard()
Now that it is OK to call git_hash_discard() even after finalizing the
hash, we no longer need the ctx_valid bool added by a2d8ea5a76 (http:
discard hash in dumb-http http_object_request, 2026-07-02).

Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-07 21:56:00 -07:00
Jeff King 6728cfba89 csum-file: use idempotent git_hash_discard()
Now that it is safe to call git_hash_discard() even after finalizing it,
we can simplify our cleanup logic a bit. This is mostly undoing a few
bits of 64337aecde (csum-file: always finalize or discard hash,
2026-07-02):

  - We no longer need a separate free_hashfile_memory() function for
    finalize_hashfile(). It can just call free_hashfile(), which will
    now discard (or not) the hash as appropriate.

  - When f->skip_hash is set, we don't need to discard; we can rely on
    free_hashfile() to do it.

Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-07 21:56:00 -07:00
Jeff King 2c51615d3f hash: make git_hash_discard() idempotent
You must always either finalize or discard a hash context to release any
resources, but you must call only one such function. This creates extra
work for some callers, since their cleanup code paths need to know
whether they got there via their happy path (and the finalization
happened) or due to an error (in which case they need to discard).

Let's add an "active" flag that turns a redundant discard into a noop.
That lets you safely do this:

    git_hash_init(&ctx, algo);
    ...
    if (some_error)
            goto out;
    ...
    git_hash_final(result, &ctx);

  out:
    git_hash_discard(&ctx);

This should avoid future errors, and will also let us simplify a few
existing callers (in future patches).

Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-07 21:56:00 -07:00
Jeff King 90a55e3a51 hash: document function pointers and wrappers
We want people to use the git_hash_*() wrappers rather than the bare
function pointers in the git_hash_algo struct. Let's document them
rather than the bare pointers, and warn people away from the pointers.
Coccinelle will eventually force the use of the wrappers, but it's
helpful to lead readers in the right direction from the start.

While we're here we can document a few other bits of wisdom I've turned
up while working in this area:

  - You have to initialize the destination of a git_hash_clone(). This
    is something we may eventually change for efficiency, but we should
    definitely document the requirement for now.

  - You must eventually finalize or discard a hash, since some backends
    may allocate resources during initialization.

Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-07 21:56:00 -07:00
Jeff King b87af5aa77 hash: convert remaining direct function calls
The previous patch added a coccinelle rule to make sure callers always
use git_hash_init() rather than direct function pointers from the algo
struct.

Let's do the same for the rest of the git_hash_*() wrappers. I split
these out because they're a bit different: they implicitly use the algop
pointer in the git_hash_ctx. So when we convert:

  -algo->update_fn(&ctx, buf, len);
  +git_hash_update(&ctx, buf, len);

we drop the reference to algo entirely! But this is always going to be
the right thing. If "algo" does not match what is in ctx.algop, then
we'd already be invoking undefined behavior.

So in addition to making it possible to add more logic to the
git_hash_*() functions, we're avoiding the need to pass around the extra
algo pointer and make sure that it matches what's in "ctx".

The rest of the patch is the mechanical application of that coccinelle
patch, plus a minor cleanup in test-synthesize.c to drop a now-unused
function parameter (since we don't have to pass around the algo
separately anymore).

Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-07 21:56:00 -07:00
Jeff King 9b204b825b hash: use git_hash_init() consistently
We'd like to add more logic to git_hash_init(), but many callers skip it
and call algop->init_fn() directly. Let's make sure we're consistently
using the wrapper by adding a coccinelle rule.

Besides the coccinelle file itself, this is a purely mechanical
conversion based on the patch it generates. There should be no bare
init_fn() calls left (except for the one in the wrapper).

Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2026-07-07 21:56:00 -07:00