Add a mutex to protect against simultaneous read/write to backend config

This addresses issues found by race detector.
This commit is contained in:
Archangel_SDY 2018-12-06 21:24:41 +08:00
parent 9122c08b3e
commit d58dbde5e3
3 changed files with 20 additions and 9 deletions

View file

@ -36,8 +36,8 @@ import (
// syncSecret synchronizes the content of a TLS Secret (certificate(s), secret // syncSecret synchronizes the content of a TLS Secret (certificate(s), secret
// key) with the filesystem. The resulting files can be used by NGINX. // key) with the filesystem. The resulting files can be used by NGINX.
func (s k8sStore) syncSecret(key string) { func (s k8sStore) syncSecret(key string) {
s.mu.Lock() s.syncSecretMu.Lock()
defer s.mu.Unlock() defer s.syncSecretMu.Unlock()
klog.V(3).Infof("Syncing Secret %q", key) klog.V(3).Infof("Syncing Secret %q", key)

View file

@ -211,8 +211,11 @@ type k8sStore struct {
// updateCh // updateCh
updateCh *channels.RingChannel updateCh *channels.RingChannel
// mu protects against simultaneous invocations of syncSecret // syncSecretMu protects against simultaneous invocations of syncSecret
mu *sync.Mutex syncSecretMu *sync.Mutex
// backendConfigMu protects against simultaneous read/write of backendConfig
backendConfigMu *sync.RWMutex
defaultSSLCertificate string defaultSSLCertificate string
@ -239,7 +242,8 @@ func New(checkOCSP bool,
filesystem: fs, filesystem: fs,
updateCh: updateCh, updateCh: updateCh,
backendConfig: ngx_config.NewDefault(), backendConfig: ngx_config.NewDefault(),
mu: &sync.Mutex{}, syncSecretMu: &sync.Mutex{},
backendConfigMu: &sync.RWMutex{},
secretIngressMap: NewObjectRefMap(), secretIngressMap: NewObjectRefMap(),
defaultSSLCertificate: defaultSSLCertificate, defaultSSLCertificate: defaultSSLCertificate,
isDynamicCertificatesEnabled: isDynamicCertificatesEnabled, isDynamicCertificatesEnabled: isDynamicCertificatesEnabled,
@ -798,15 +802,21 @@ func (s k8sStore) writeSSLSessionTicketKey(cmap *corev1.ConfigMap, fileName stri
} }
// GetDefaultBackend returns the default backend // GetDefaultBackend returns the default backend
func (s k8sStore) GetDefaultBackend() defaults.Backend { func (s *k8sStore) GetDefaultBackend() defaults.Backend {
return s.backendConfig.Backend return s.GetBackendConfiguration().Backend
} }
func (s k8sStore) GetBackendConfiguration() ngx_config.Configuration { func (s *k8sStore) GetBackendConfiguration() ngx_config.Configuration {
s.backendConfigMu.RLock()
defer s.backendConfigMu.RUnlock()
return s.backendConfig return s.backendConfig
} }
func (s *k8sStore) setConfig(cmap *corev1.ConfigMap) { func (s *k8sStore) setConfig(cmap *corev1.ConfigMap) {
s.backendConfigMu.Lock()
defer s.backendConfigMu.Unlock()
s.backendConfig = ngx_template.ReadConfig(cmap.Data) s.backendConfig = ngx_template.ReadConfig(cmap.Data)
s.writeSSLSessionTicketKey(cmap, "/etc/nginx/tickets.key") s.writeSSLSessionTicketKey(cmap, "/etc/nginx/tickets.key")
} }

View file

@ -865,7 +865,8 @@ func newStore(t *testing.T) *k8sStore {
sslStore: NewSSLCertTracker(), sslStore: NewSSLCertTracker(),
filesystem: fs, filesystem: fs,
updateCh: channels.NewRingChannel(10), updateCh: channels.NewRingChannel(10),
mu: new(sync.Mutex), syncSecretMu: new(sync.Mutex),
backendConfigMu: new(sync.RWMutex),
secretIngressMap: NewObjectRefMap(), secretIngressMap: NewObjectRefMap(),
pod: pod, pod: pod,
} }