From a1c91b3e85c8b6f18f04dc5c361a87f82c927bea Mon Sep 17 00:00:00 2001 From: Markus Rudy Date: Fri, 14 Jun 2024 20:42:51 +0200 Subject: [PATCH] coordinator: make history thread-safe --- coordinator/history/history.go | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/coordinator/history/history.go b/coordinator/history/history.go index 535d33063..8ea762865 100644 --- a/coordinator/history/history.go +++ b/coordinator/history/history.go @@ -13,6 +13,7 @@ import ( "fmt" "hash" "os" + "sync/atomic" "github.com/spf13/afero" ) @@ -28,7 +29,7 @@ const ( type History struct { store Store hashFun func() hash.Hash - signingKey *ecdsa.PrivateKey + signingKey atomic.Pointer[ecdsa.PrivateKey] } // New creates a new History backed by the default filesystem store. @@ -55,7 +56,7 @@ func NewWithStore(store Store) *History { // ConfigureSigningKey sets the signing key for validation and signing of the protected history parts. func (h *History) ConfigureSigningKey(signingKey *ecdsa.PrivateKey) { - h.signingKey = signingKey + h.signingKey.Store(signingKey) } // GetManifest returns the manifest for the given hash. @@ -98,7 +99,8 @@ func (h *History) SetTransition(transition *Transition) ([HashSize]byte, error) // GetLatest returns the verified transition for the given hash. func (h *History) GetLatest() (*LatestTransition, error) { - if h.signingKey == nil { + signingKey := h.signingKey.Load() + if signingKey == nil { return nil, errors.New("signing key not configured") } transitionBytes, err := h.store.Get("transitions/latest") @@ -109,7 +111,7 @@ func (h *History) GetLatest() (*LatestTransition, error) { if err := latestTransition.unmarshalBinary(transitionBytes); err != nil { return nil, fmt.Errorf("unmarshaling latest transition: %w", err) } - if err := latestTransition.verify(&h.signingKey.PublicKey); err != nil { + if err := latestTransition.verify(&signingKey.PublicKey); err != nil { return nil, fmt.Errorf("verifying latest transition: %w", err) } return &latestTransition, nil @@ -129,10 +131,11 @@ func (h *History) HasLatest() (bool, error) { // SetLatest signs and sets the latest transition if the current latest is equal to oldT. func (h *History) SetLatest(oldT, newT *LatestTransition) error { - if h.signingKey == nil { + signingKey := h.signingKey.Load() + if signingKey == nil { return errors.New("signing key not configured") } - if err := newT.sign(h.signingKey); err != nil { + if err := newT.sign(signingKey); err != nil { return fmt.Errorf("signing latest transition: %w", err) } if err := h.store.CompareAndSwap("transitions/latest", oldT.marshalBinary(), newT.marshalBinary()); err != nil {