@@ -712,41 +712,47 @@ void delete(RefDirectoryUpdate update) throws IOException {
712
712
}
713
713
String name = dst .getName ();
714
714
715
- // Write the packed-refs file using an atomic update. We might
716
- // wind up reading it twice, before and after the lock, to ensure
717
- // we don't miss an edit made externally.
718
- PackedRefList packed = getPackedRefs ();
719
- if (packed .contains (name )) {
720
- inProcessPackedRefsLock .lock ();
715
+ // Get and keep the packed-refs lock while updating packed-refs and
716
+ // removing any loose ref
717
+ inProcessPackedRefsLock .lock ();
718
+ try {
719
+ LockFile lck = lockPackedRefsOrThrow ();
721
720
try {
722
- LockFile lck = lockPackedRefsOrThrow ();
723
- try {
721
+ // Write the packed-refs file using an atomic update. We might
722
+ // wind up reading it twice, before and after checking if the
723
+ // ref to delete is included or not, to ensure
724
+ // we don't rely on a PackedRefList that is a result of in-memory
725
+ // or NFS caching.
726
+ PackedRefList packed = getPackedRefs ();
727
+ if (packed .contains (name )) {
728
+ // Force update our packed-refs snapshot before writing
724
729
packed = refreshPackedRefs ();
725
730
int idx = packed .find (name );
726
731
if (0 <= idx ) {
727
732
commitPackedRefs (lck , packed .remove (idx ), packed , true );
728
733
}
729
- } finally {
730
- lck .unlock ();
731
734
}
732
- } finally {
733
- inProcessPackedRefsLock .unlock ();
734
- }
735
- }
736
735
737
- RefList <LooseRef > curLoose , newLoose ;
738
- do {
739
- curLoose = looseRefs .get ();
740
- int idx = curLoose .find (name );
741
- if (idx < 0 )
742
- break ;
743
- newLoose = curLoose .remove (idx );
744
- } while (!looseRefs .compareAndSet (curLoose , newLoose ));
736
+ RefList <LooseRef > curLoose , newLoose ;
737
+ do {
738
+ curLoose = looseRefs .get ();
739
+ int idx = curLoose .find (name );
740
+ if (idx < 0 ) {
741
+ break ;
742
+ }
743
+ newLoose = curLoose .remove (idx );
744
+ } while (!looseRefs .compareAndSet (curLoose , newLoose ));
745
745
746
- int levels = levelsIn (name ) - 2 ;
747
- delete (logFor (name ), levels );
748
- if (dst .getStorage ().isLoose ()) {
749
- deleteAndUnlock (fileFor (name ), levels , update );
746
+ int levels = levelsIn (name ) - 2 ;
747
+ delete (logFor (name ), levels );
748
+ if (dst .getStorage ().isLoose ()) {
749
+ deleteAndUnlock (fileFor (name ), levels , update );
750
+ }
751
+ } finally {
752
+ lck .unlock ();
753
+ }
754
+ } finally {
755
+ inProcessPackedRefsLock .unlock ();
750
756
}
751
757
752
758
modCnt .incrementAndGet ();
0 commit comments