From 67fd60275a6187c41c4944545c2145cd28bc330d Mon Sep 17 00:00:00 2001 From: r-ricci Date: Mon, 11 Jul 2022 18:34:06 +0100 Subject: [PATCH] union: fix panic due to misalignment of struct field in 32 bit architectures `FS.cacheExpiry` is accessed through sync/atomic. According to the documentation, "On ARM, 386, and 32-bit MIPS, it is the caller's responsibility to arrange for 64-bit alignment of 64-bit words accessed atomically. The first word in a variable or in an allocated struct, array, or slice can be relied upon to be 64-bit aligned." Before commit 1d2fe0d8564bc679ece166c24b24e6fe7dc1455c this field was aligned, but then a new field was added to the structure, causing the test suite to panic on linux/386. No other field is used with sync/atomic, so `cacheExpiry` can just be placed at the beginning of the stuct to ensure it is always aligned. --- backend/union/upstream/upstream.go | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/backend/union/upstream/upstream.go b/backend/union/upstream/upstream.go index 35b477f79..7b9f44fd2 100644 --- a/backend/union/upstream/upstream.go +++ b/backend/union/upstream/upstream.go @@ -24,6 +24,10 @@ var ( // Fs is a wrap of any fs and its configs type Fs struct { + // In order to ensure memory alignment on 32-bit architectures + // when this field is accessed through sync/atomic functions, + // it must be the first entry in the struct + cacheExpiry int64 // usage cache expiry time fs.Fs RootFs fs.Fs RootPath string @@ -32,7 +36,6 @@ type Fs struct { creatable bool usage *fs.Usage // Cache the usage cacheTime time.Duration // cache duration - cacheExpiry int64 // usage cache expiry time cacheMutex sync.RWMutex cacheOnce sync.Once cacheUpdate bool // if the cache is updating