summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Documentation/git-receive-pack.txt3
-rw-r--r--refs.c6
-rwxr-xr-xt/t5547-push-quarantine.sh11
3 files changed, 19 insertions, 1 deletions
diff --git a/Documentation/git-receive-pack.txt b/Documentation/git-receive-pack.txt
index 7267ecfbe8..86a4b32f0f 100644
--- a/Documentation/git-receive-pack.txt
+++ b/Documentation/git-receive-pack.txt
@@ -239,7 +239,8 @@ This has a few user-visible effects and caveats:
3. The `pre-receive` hook MUST NOT update any refs to point to
quarantined objects. Other programs accessing the repository will
not be able to see the objects (and if the pre-receive hook fails,
- those refs would become corrupted).
+ those refs would become corrupted). For safety, any ref updates
+ from within `pre-receive` are automatically rejected.
SEE ALSO
diff --git a/refs.c b/refs.c
index 5ffdd778d9..916b0d5fa5 100644
--- a/refs.c
+++ b/refs.c
@@ -1465,6 +1465,12 @@ int ref_transaction_commit(struct ref_transaction *transaction,
{
struct ref_store *refs = get_ref_store(NULL);
+ if (getenv(GIT_QUARANTINE_ENVIRONMENT)) {
+ strbuf_addstr(err,
+ _("ref updates forbidden inside quarantine environment"));
+ return -1;
+ }
+
return refs->be->transaction_commit(refs, transaction, err);
}
diff --git a/t/t5547-push-quarantine.sh b/t/t5547-push-quarantine.sh
index 1e5d32d068..462bfc9cba 100755
--- a/t/t5547-push-quarantine.sh
+++ b/t/t5547-push-quarantine.sh
@@ -33,4 +33,15 @@ test_expect_success 'rejected objects are removed' '
test_cmp expect actual
'
+test_expect_success 'updating a ref from quarantine is forbidden' '
+ git init --bare update.git &&
+ write_script update.git/hooks/pre-receive <<-\EOF &&
+ read old new refname
+ git update-ref refs/heads/unrelated $new
+ exit 1
+ EOF
+ test_must_fail git push update.git HEAD &&
+ git -C update.git fsck
+'
+
test_done