From 0d3b86ad6aaea166508ee2d12728ef7f996c3555 Mon Sep 17 00:00:00 2001 From: Tim Gross Date: Fri, 9 Dec 2022 15:03:32 -0500 Subject: [PATCH] csi: avoid a nil pointer when handling plugin events If a plugin crashes quickly enough, we can get into a situation where the deregister function is called before it's ever registered. Safely handle the resulting nil pointer in the dynamic registry by not emitting a plugin event, but also update the plugin event handler to tolerate nil pointers in case we wire it up elsewhere in the future. --- .changelog/15518.txt | 3 +++ client/dynamicplugins/registry.go | 12 +++++++----- client/pluginmanager/csimanager/manager.go | 2 +- 3 files changed, 11 insertions(+), 6 deletions(-) create mode 100644 .changelog/15518.txt diff --git a/.changelog/15518.txt b/.changelog/15518.txt new file mode 100644 index 000000000000..d081950b9b47 --- /dev/null +++ b/.changelog/15518.txt @@ -0,0 +1,3 @@ +```release-note:bug +csi: Fixed a bug where a crashing plugin could panic the Nomad client +``` diff --git a/client/dynamicplugins/registry.go b/client/dynamicplugins/registry.go index 3059c1a2763c..4515c64fb684 100644 --- a/client/dynamicplugins/registry.go +++ b/client/dynamicplugins/registry.go @@ -269,12 +269,14 @@ func (d *dynamicRegistry) DeregisterPlugin(ptype, name, allocID string) error { } } - broadcaster := d.broadcasterForPluginType(ptype) - event := &PluginUpdateEvent{ - EventType: EventTypeDeregistered, - Info: info, + if info != nil { + broadcaster := d.broadcasterForPluginType(ptype) + event := &PluginUpdateEvent{ + EventType: EventTypeDeregistered, + Info: info, + } + broadcaster.broadcast(event) } - broadcaster.broadcast(event) return d.sync() } diff --git a/client/pluginmanager/csimanager/manager.go b/client/pluginmanager/csimanager/manager.go index a5b2f51cd446..178b0fe1513e 100644 --- a/client/pluginmanager/csimanager/manager.go +++ b/client/pluginmanager/csimanager/manager.go @@ -149,7 +149,7 @@ func (c *csiManager) resyncPluginsFromRegistry(ptype string) { // handlePluginEvent syncs a single event against the plugin registry func (c *csiManager) handlePluginEvent(event *dynamicplugins.PluginUpdateEvent) { - if event == nil { + if event == nil || event.Info == nil { return } c.logger.Trace("dynamic plugin event",