The following pull request was submitted through Github.
It can be accessed and reviewed at: https://github.com/lxc/lxd/pull/8254

This e-mail was sent by the LXC bot, direct replies will not reach the author
unless they happen to be subscribed to this list.

=== Description (from pull-request) ===
Fixes 8253
From 1f8d31f61d7f375b5fd8029d4d79d4ce6da8292e Mon Sep 17 00:00:00 2001
From: Thomas Parrott <thomas.parr...@canonical.com>
Date: Tue, 15 Dec 2020 12:41:08 +0000
Subject: [PATCH 1/2] lxd/instance/drivers/qmp/monitor: Handle closed event
 channel from qmp package in run

Fixes #8253

Signed-off-by: Thomas Parrott <thomas.parr...@canonical.com>
---
 lxd/instance/drivers/qmp/monitor.go | 20 +++++++++++++++-----
 1 file changed, 15 insertions(+), 5 deletions(-)

diff --git a/lxd/instance/drivers/qmp/monitor.go 
b/lxd/instance/drivers/qmp/monitor.go
index 20c6dd4d01..ea564e6080 100644
--- a/lxd/instance/drivers/qmp/monitor.go
+++ b/lxd/instance/drivers/qmp/monitor.go
@@ -12,6 +12,7 @@ import (
        "github.com/digitalocean/go-qemu/qmp"
 
        "github.com/lxc/lxd/shared"
+       "github.com/lxc/lxd/shared/logger"
 )
 
 var monitors = map[string]*Monitor{}
@@ -126,13 +127,22 @@ func (m *Monitor) run() error {
                        select {
                        case <-m.chDisconnect:
                                return
-                       case e := <-chEvents:
-                               if e.Event == "" {
-                                       continue
+                       case e, more := <-chEvents:
+                               // Deliver non-empty events to the event 
handler.
+                               if m.eventHandler != nil && e.Event != "" {
+                                       go m.eventHandler(e.Event, e.Data)
                                }
 
-                               if m.eventHandler != nil {
-                                       go m.eventHandler(e.Event, e.Data)
+                               // Event channel is closed, lets disconnect.
+                               if !more {
+                                       m.Disconnect()
+                                       return
+                               }
+
+                               if e.Event == "" {
+                                       logger.Warnf("Unexpected empty event 
received from qmp event channel")
+                                       time.Sleep(time.Second) // Don't busy 
wait if we receive a lot of these.
+                                       continue
                                }
 
                                // Check if the ringbuffer was updated 
(non-blocking).

From 2ab69cfc1fa49211b3fb3de0ed9ed29ac78c6e0a Mon Sep 17 00:00:00 2001
From: Thomas Parrott <thomas.parr...@canonical.com>
Date: Tue, 15 Dec 2020 12:41:56 +0000
Subject: [PATCH 2/2] lxd/instance/drivers/driver/qemu: Logs when instance is
 stopped in getMonitorEventHandler

And removes some references to the instance in the function returned from 
getMonitorEventHandler so they are not kept in memory.

Signed-off-by: Thomas Parrott <thomas.parr...@canonical.com>
---
 lxd/instance/drivers/driver_qemu.go | 9 +++++++--
 1 file changed, 7 insertions(+), 2 deletions(-)

diff --git a/lxd/instance/drivers/driver_qemu.go 
b/lxd/instance/drivers/driver_qemu.go
index d01f47a3f7..b6168a3f6e 100644
--- a/lxd/instance/drivers/driver_qemu.go
+++ b/lxd/instance/drivers/driver_qemu.go
@@ -343,9 +343,12 @@ func (d *qemu) getStoragePool() (storagePools.Pool, error) 
{
 }
 
 func (d *qemu) getMonitorEventHandler() func(event string, data 
map[string]interface{}) {
+       // Create local variables from device properties we need so as not to 
keep references to device around
+       // after we have returned the callback function.
        projectName := d.Project()
        instanceName := d.Name()
        state := d.state
+       logger := d.logger
 
        return func(event string, data map[string]interface{}) {
                if !shared.StringInSlice(event, []string{"SHUTDOWN"}) {
@@ -354,11 +357,13 @@ func (d *qemu) getMonitorEventHandler() func(event 
string, data map[string]inter
 
                inst, err := instance.LoadByProjectAndName(state, projectName, 
instanceName)
                if err != nil {
-                       d.logger.Error("Failed to load instance", 
log.Ctx{"err": err})
+                       logger.Error("Failed to load instance", log.Ctx{"err": 
err})
                        return
                }
 
                if event == "SHUTDOWN" {
+                       logger.Debug("Instance stopped")
+
                        target := "stop"
                        entry, ok := data["reason"]
                        if ok && entry == "guest-reset" {
@@ -367,7 +372,7 @@ func (d *qemu) getMonitorEventHandler() func(event string, 
data map[string]inter
 
                        err = inst.(*qemu).onStop(target)
                        if err != nil {
-                               d.logger.Error("Failed to cleanly stop 
instance", log.Ctx{"err": err})
+                               logger.Error("Failed to cleanly stop instance", 
log.Ctx{"err": err})
                                return
                        }
                }
_______________________________________________
lxc-devel mailing list
lxc-devel@lists.linuxcontainers.org
http://lists.linuxcontainers.org/listinfo/lxc-devel

Reply via email to