The function remove_lock_file_on_signal() is used as a signal handler.
It is not realistic to make the signal handler conform strictly to the
C standard, which is very restrictive about what a signal handler is
allowed to do.  But let's increase the likelihood that it will work:

The lock_file_list global variable and several fields from struct
lock_file are used by the signal handler.  Declare those values
"volatile" to increase the chance that the signal handler will see a
valid object state.

Suggested-by: Johannes Sixt <j.s...@viscovery.net>
Signed-off-by: Michael Haggerty <mhag...@alum.mit.edu>
---
 cache.h    | 6 +++---
 lockfile.c | 2 +-
 refs.c     | 5 +++--
 3 files changed, 7 insertions(+), 6 deletions(-)

diff --git a/cache.h b/cache.h
index b7af173..9019c7d 100644
--- a/cache.h
+++ b/cache.h
@@ -538,10 +538,10 @@ extern int refresh_index(struct index_state *, unsigned 
int flags, const struct
 #define LOCK_SUFFIX_LEN 5
 
 struct lock_file {
-       struct lock_file *next;
+       struct lock_file *volatile next;
        volatile sig_atomic_t active;
-       int fd;
-       pid_t owner;
+       volatile int fd;
+       volatile pid_t owner;
        char on_list;
        char filename[PATH_MAX];
 };
diff --git a/lockfile.c b/lockfile.c
index 50a0541..fce53f1 100644
--- a/lockfile.c
+++ b/lockfile.c
@@ -69,7 +69,7 @@
  * See Documentation/api-lockfile.txt for more information.
  */
 
-static struct lock_file *lock_file_list;
+static struct lock_file *volatile lock_file_list;
 static const char *alternate_index_output;
 
 static void remove_lock_file(void)
diff --git a/refs.c b/refs.c
index cb2f825..db8057c 100644
--- a/refs.c
+++ b/refs.c
@@ -2213,15 +2213,16 @@ int commit_packed_refs(void)
        struct packed_ref_cache *packed_ref_cache =
                get_packed_ref_cache(&ref_cache);
        int error = 0;
+       int fd;
 
        if (!packed_ref_cache->lock)
                die("internal error: packed-refs not locked");
        write_or_die(packed_ref_cache->lock->fd,
                     PACKED_REFS_HEADER, strlen(PACKED_REFS_HEADER));
 
+       fd = packed_ref_cache->lock->fd;
        do_for_each_entry_in_dir(get_packed_ref_dir(packed_ref_cache),
-                                0, write_packed_entry_fn,
-                                &packed_ref_cache->lock->fd);
+                                0, write_packed_entry_fn, &fd);
        if (commit_lock_file(packed_ref_cache->lock))
                error = -1;
        packed_ref_cache->lock = NULL;
-- 
1.9.1

--
To unsubscribe from this list: send the line "unsubscribe git" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

Reply via email to