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

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) ===

From 2a5182f52015de80678532a46ec2ae7db02848f8 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?St=C3=A9phane=20Graber?= <stgra...@ubuntu.com>
Date: Wed, 20 Nov 2019 14:54:37 -0500
Subject: [PATCH 1/4] lxd/storage: Rename storagePoolVolumeUsedByContainersGet
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Signed-off-by: Stéphane Graber <stgra...@ubuntu.com>
---
 lxd/storage.go               |  2 +-
 lxd/storage_btrfs.go         |  2 +-
 lxd/storage_ceph.go          |  2 +-
 lxd/storage_cephfs.go        |  2 +-
 lxd/storage_dir.go           |  2 +-
 lxd/storage_lvm.go           |  2 +-
 lxd/storage_volumes_utils.go | 10 +++++-----
 lxd/storage_zfs.go           |  2 +-
 8 files changed, 12 insertions(+), 12 deletions(-)

diff --git a/lxd/storage.go b/lxd/storage.go
index 163bff5435..138f7d144f 100644
--- a/lxd/storage.go
+++ b/lxd/storage.go
@@ -488,7 +488,7 @@ func storagePoolVolumeAttachInit(s *state.State, poolName 
string, volumeName str
                logger.Debugf("Shifting storage volume")
 
                if !shared.IsTrue(poolVolumePut.Config["security.shifted"]) {
-                       volumeUsedBy, err := 
storagePoolVolumeUsedByContainersGet(s, "default", poolName, volumeName)
+                       volumeUsedBy, err := 
storagePoolVolumeUsedByInstancesGet(s, "default", poolName, volumeName)
                        if err != nil {
                                return nil, err
                        }
diff --git a/lxd/storage_btrfs.go b/lxd/storage_btrfs.go
index 1d31793083..99ef097b09 100644
--- a/lxd/storage_btrfs.go
+++ b/lxd/storage_btrfs.go
@@ -747,7 +747,7 @@ func (s *storageBtrfs) StoragePoolVolumeRename(newName 
string) error {
                return err
        }
 
-       usedBy, err := storagePoolVolumeUsedByContainersGet(s.s, "default", 
s.pool.Name, s.volume.Name)
+       usedBy, err := storagePoolVolumeUsedByInstancesGet(s.s, "default", 
s.pool.Name, s.volume.Name)
        if err != nil {
                return err
        }
diff --git a/lxd/storage_ceph.go b/lxd/storage_ceph.go
index 20d619fe22..45a21a4f19 100644
--- a/lxd/storage_ceph.go
+++ b/lxd/storage_ceph.go
@@ -675,7 +675,7 @@ func (s *storageCeph) StoragePoolVolumeRename(newName 
string) error {
                return err
        }
 
-       usedBy, err := storagePoolVolumeUsedByContainersGet(s.s, "default", 
s.pool.Name, s.volume.Name)
+       usedBy, err := storagePoolVolumeUsedByInstancesGet(s.s, "default", 
s.pool.Name, s.volume.Name)
        if err != nil {
                return err
        }
diff --git a/lxd/storage_cephfs.go b/lxd/storage_cephfs.go
index b0b5622297..495165b75d 100644
--- a/lxd/storage_cephfs.go
+++ b/lxd/storage_cephfs.go
@@ -588,7 +588,7 @@ func (s *storageCephFs) StoragePoolVolumeRename(newName 
string) error {
        logger.Infof(`Renaming CEPHFS storage volume on storage pool "%s" from 
"%s" to "%s`, s.pool.Name, s.volume.Name, newName)
 
        // Sanity check
-       usedBy, err := storagePoolVolumeUsedByContainersGet(s.s, "default", 
s.pool.Name, s.volume.Name)
+       usedBy, err := storagePoolVolumeUsedByInstancesGet(s.s, "default", 
s.pool.Name, s.volume.Name)
        if err != nil {
                return err
        }
diff --git a/lxd/storage_dir.go b/lxd/storage_dir.go
index 9355713cc2..71073bb63d 100644
--- a/lxd/storage_dir.go
+++ b/lxd/storage_dir.go
@@ -468,7 +468,7 @@ func (s *storageDir) StoragePoolVolumeRename(newName 
string) error {
                return err
        }
 
-       usedBy, err := storagePoolVolumeUsedByContainersGet(s.s, "default", 
s.pool.Name, s.volume.Name)
+       usedBy, err := storagePoolVolumeUsedByInstancesGet(s.s, "default", 
s.pool.Name, s.volume.Name)
        if err != nil {
                return err
        }
diff --git a/lxd/storage_lvm.go b/lxd/storage_lvm.go
index ce7aa01137..2f0166193d 100644
--- a/lxd/storage_lvm.go
+++ b/lxd/storage_lvm.go
@@ -885,7 +885,7 @@ func (s *storageLvm) StoragePoolVolumeRename(newName 
string) error {
                return err
        }
 
-       usedBy, err := storagePoolVolumeUsedByContainersGet(s.s, "default", 
s.pool.Name, s.volume.Name)
+       usedBy, err := storagePoolVolumeUsedByInstancesGet(s.s, "default", 
s.pool.Name, s.volume.Name)
        if err != nil {
                return err
        }
diff --git a/lxd/storage_volumes_utils.go b/lxd/storage_volumes_utils.go
index 2774cd4b30..464b90a0c7 100644
--- a/lxd/storage_volumes_utils.go
+++ b/lxd/storage_volumes_utils.go
@@ -214,13 +214,13 @@ func storagePoolVolumeUpdate(state *state.State, poolName 
string, volumeName str
        return nil
 }
 
-func storagePoolVolumeUsedByContainersGet(s *state.State, project, poolName 
string, volumeName string) ([]string, error) {
+func storagePoolVolumeUsedByInstancesGet(s *state.State, project, poolName 
string, volumeName string) ([]string, error) {
        insts, err := instanceLoadByProject(s, project)
        if err != nil {
                return []string{}, err
        }
 
-       ctsUsingVolume := []string{}
+       instUsingVolume := []string{}
        for _, inst := range insts {
                for _, dev := range inst.LocalDevices() {
                        if dev["type"] != "disk" {
@@ -228,13 +228,13 @@ func storagePoolVolumeUsedByContainersGet(s *state.State, 
project, poolName stri
                        }
 
                        if dev["pool"] == poolName && dev["source"] == 
volumeName {
-                               ctsUsingVolume = append(ctsUsingVolume, 
inst.Name())
+                               instUsingVolume = append(instUsingVolume, 
inst.Name())
                                break
                        }
                }
        }
 
-       return ctsUsingVolume, nil
+       return instUsingVolume, nil
 }
 
 func storagePoolVolumeUpdateUsers(d *Daemon, oldPoolName string,
@@ -436,7 +436,7 @@ func storagePoolVolumeUsedByGet(s *state.State, project, 
poolName string, volume
        }
 
        // Look for containers using this volume
-       ctsUsingVolume, err := storagePoolVolumeUsedByContainersGet(s, project, 
poolName, volumeName)
+       ctsUsingVolume, err := storagePoolVolumeUsedByInstancesGet(s, project, 
poolName, volumeName)
        if err != nil {
                return []string{}, err
        }
diff --git a/lxd/storage_zfs.go b/lxd/storage_zfs.go
index 26c5b4af2d..a19e435b4a 100644
--- a/lxd/storage_zfs.go
+++ b/lxd/storage_zfs.go
@@ -729,7 +729,7 @@ func (s *storageZfs) StoragePoolVolumeRename(newName 
string) error {
        logger.Infof(`Renaming ZFS storage volume on storage pool "%s" from 
"%s" to "%s`,
                s.pool.Name, s.volume.Name, newName)
 
-       usedBy, err := storagePoolVolumeUsedByContainersGet(s.s, "default", 
s.pool.Name, s.volume.Name)
+       usedBy, err := storagePoolVolumeUsedByInstancesGet(s.s, "default", 
s.pool.Name, s.volume.Name)
        if err != nil {
                return err
        }

From 3eba8b03cff2e534e4029eaacfe3d27d774dc239 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?St=C3=A9phane=20Graber?= <stgra...@ubuntu.com>
Date: Wed, 20 Nov 2019 14:54:57 -0500
Subject: [PATCH 2/4] lxd/storage: Rename
 storagePoolVolumeUsedByRunningInstancesWithProfilesGet
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Signed-off-by: Stéphane Graber <stgra...@ubuntu.com>
---
 lxd/storage_volumes.go       |  4 ++--
 lxd/storage_volumes_utils.go | 12 ++++++------
 2 files changed, 8 insertions(+), 8 deletions(-)

diff --git a/lxd/storage_volumes.go b/lxd/storage_volumes.go
index 0e04c9b611..9c8954091d 100644
--- a/lxd/storage_volumes.go
+++ b/lxd/storage_volumes.go
@@ -596,7 +596,7 @@ func storagePoolVolumeTypePost(d *Daemon, r *http.Request, 
volumeTypeName string
        }
 
        // Check if a running container is using it.
-       ctsUsingVolume, err := 
storagePoolVolumeUsedByRunningContainersWithProfilesGet(d.State(), poolName, 
volumeName, volumeTypeName, true)
+       ctsUsingVolume, err := 
storagePoolVolumeUsedByRunningInstancesWithProfilesGet(d.State(), poolName, 
volumeName, volumeTypeName, true)
        if err != nil {
                return response.SmartError(err)
        }
@@ -1010,7 +1010,7 @@ func storagePoolVolumeTypePut(d *Daemon, r *http.Request, 
volumeTypeName string)
        } else {
 
                if req.Restore != "" {
-                       ctsUsingVolume, err := 
storagePoolVolumeUsedByRunningContainersWithProfilesGet(d.State(), poolName, 
vol.Name, storagePoolVolumeTypeNameCustom, true)
+                       ctsUsingVolume, err := 
storagePoolVolumeUsedByRunningInstancesWithProfilesGet(d.State(), poolName, 
vol.Name, storagePoolVolumeTypeNameCustom, true)
                        if err != nil {
                                return response.InternalError(err)
                        }
diff --git a/lxd/storage_volumes_utils.go b/lxd/storage_volumes_utils.go
index 464b90a0c7..dd5a672b34 100644
--- a/lxd/storage_volumes_utils.go
+++ b/lxd/storage_volumes_utils.go
@@ -43,7 +43,7 @@ var supportedVolumeTypesExceptImages = 
[]int{storagePoolVolumeTypeContainer, sto
 var supportedVolumeTypes = append(supportedVolumeTypesExceptImages, 
storagePoolVolumeTypeImage)
 
 func init() {
-       storagePools.VolumeUsedByInstancesWithProfiles = 
storagePoolVolumeUsedByRunningContainersWithProfilesGet
+       storagePools.VolumeUsedByInstancesWithProfiles = 
storagePoolVolumeUsedByRunningInstancesWithProfilesGet
 }
 
 func storagePoolVolumeTypeNameToAPIEndpoint(volumeTypeName string) (string, 
error) {
@@ -178,7 +178,7 @@ func storagePoolVolumeUpdate(state *state.State, poolName 
string, volumeName str
 
        // Confirm that no containers are running when changing shifted state
        if newConfig["security.shifted"] != oldConfig["security.shifted"] {
-               ctsUsingVolume, err := 
storagePoolVolumeUsedByRunningContainersWithProfilesGet(state, poolName, 
volumeName, storagePoolVolumeTypeNameCustom, true)
+               ctsUsingVolume, err := 
storagePoolVolumeUsedByRunningInstancesWithProfilesGet(state, poolName, 
volumeName, storagePoolVolumeTypeNameCustom, true)
                if err != nil {
                        return err
                }
@@ -371,7 +371,7 @@ func storagePoolVolumeUpdateUsers(d *Daemon, oldPoolName 
string,
        return nil
 }
 
-func storagePoolVolumeUsedByRunningContainersWithProfilesGet(s *state.State,
+func storagePoolVolumeUsedByRunningInstancesWithProfilesGet(s *state.State,
        poolName string, volumeName string, volumeTypeName string,
        runningOnly bool) ([]string, error) {
        insts, err := instanceLoadAll(s)
@@ -379,7 +379,7 @@ func 
storagePoolVolumeUsedByRunningContainersWithProfilesGet(s *state.State,
                return []string{}, err
        }
 
-       ctsUsingVolume := []string{}
+       instUsingVolume := []string{}
        volumeNameWithType := fmt.Sprintf("%s/%s", volumeTypeName, volumeName)
        for _, inst := range insts {
                if runningOnly && !inst.IsRunning() {
@@ -399,12 +399,12 @@ func 
storagePoolVolumeUsedByRunningContainersWithProfilesGet(s *state.State,
                        // "container////bla" but only against "container/bla".
                        cleanSource := filepath.Clean(dev["source"])
                        if cleanSource == volumeName || cleanSource == 
volumeNameWithType {
-                               ctsUsingVolume = append(ctsUsingVolume, 
inst.Name())
+                               instUsingVolume = append(instUsingVolume, 
inst.Name())
                        }
                }
        }
 
-       return ctsUsingVolume, nil
+       return instUsingVolume, nil
 }
 
 // volumeUsedBy = append(volumeUsedBy, fmt.Sprintf("/%s/containers/%s", 
version.APIVersion, ct))

From 6cc59b1729a06008a646090a2aa1a1796dc24e60 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?St=C3=A9phane=20Graber?= <stgra...@ubuntu.com>
Date: Wed, 20 Nov 2019 14:56:27 -0500
Subject: [PATCH 3/4] lxd: Have instanceLoadByProject return all instances
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Signed-off-by: Stéphane Graber <stgra...@ubuntu.com>
---
 lxd/container.go     | 2 +-
 lxd/container_lxc.go | 4 ++++
 lxd/networks.go      | 5 +++++
 3 files changed, 10 insertions(+), 1 deletion(-)

diff --git a/lxd/container.go b/lxd/container.go
index 55aaed404c..1b25779c21 100644
--- a/lxd/container.go
+++ b/lxd/container.go
@@ -1172,7 +1172,7 @@ func instanceLoadByProject(s *state.State, project 
string) ([]Instance, error) {
        err := s.Cluster.Transaction(func(tx *db.ClusterTx) error {
                filter := db.InstanceFilter{
                        Project: project,
-                       Type:    instancetype.Container,
+                       Type:    instancetype.Any,
                }
                var err error
                cts, err = tx.InstanceList(filter)
diff --git a/lxd/container_lxc.go b/lxd/container_lxc.go
index 1c800c0b08..9cd60ca5ae 100644
--- a/lxd/container_lxc.go
+++ b/lxd/container_lxc.go
@@ -745,6 +745,10 @@ func findIdmap(state *state.State, cName string, 
isolatedStr string, configBase
 
        mapentries := idmap.ByHostid{}
        for _, container := range cts {
+               if container.Type() != instancetype.Container {
+                       continue
+               }
+
                name := container.Name()
 
                /* Don't change our map Just Because. */
diff --git a/lxd/networks.go b/lxd/networks.go
index dfcb831a65..e94f8e879f 100644
--- a/lxd/networks.go
+++ b/lxd/networks.go
@@ -735,6 +735,11 @@ func networkLeasesGet(d *Daemon, r *http.Request) 
response.Response {
                                        if err != nil {
                                                continue
                                        }
+                               } else if inst.Type() == instancetype.VM {
+                                       d, err = 
inst.(*vmQemu).fillNetworkDevice(k, d)
+                                       if err != nil {
+                                               continue
+                                       }
                                }
 
                                // Record the MAC

From 252776eecc29b58ef1f40e14b584978ec2823b71 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?St=C3=A9phane=20Graber?= <stgra...@ubuntu.com>
Date: Wed, 20 Nov 2019 16:40:24 -0500
Subject: [PATCH 4/4] lxd/vm: Use leases to get IP
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Signed-off-by: Stéphane Graber <stgra...@ubuntu.com>
---
 lxd/networks.go | 71 +++++++++++++++++++++++++++++++++++++++++++++++++
 lxd/vm_qemu.go  | 59 ++++++++++++++++++++++++++++++++++++----
 2 files changed, 125 insertions(+), 5 deletions(-)

diff --git a/lxd/networks.go b/lxd/networks.go
index e94f8e879f..9505777088 100644
--- a/lxd/networks.go
+++ b/lxd/networks.go
@@ -863,6 +863,77 @@ func networkLeasesGet(d *Daemon, r *http.Request) 
response.Response {
        return response.SyncResponse(true, leases)
 }
 
+func networkGetLeaseAddresses(s *state.State, network string, hwaddr string) 
([]api.InstanceStateNetworkAddress, error) {
+       addresses := []api.InstanceStateNetworkAddress{}
+
+       leaseFile := shared.VarPath("networks", network, "dnsmasq.leases")
+       if !shared.PathExists(leaseFile) {
+               return addresses, nil
+       }
+
+       dbInfo, err := networkLoadByName(s, network)
+       if err != nil {
+               return nil, err
+       }
+
+       content, err := ioutil.ReadFile(leaseFile)
+       if err != nil {
+               return nil, err
+       }
+
+       for _, lease := range strings.Split(string(content), "\n") {
+               fields := strings.Fields(lease)
+               if len(fields) < 5 {
+                       continue
+               }
+
+               // Parse the MAC
+               mac := networkGetMacSlice(fields[1])
+               macStr := strings.Join(mac, ":")
+
+               if len(macStr) < 17 && fields[4] != "" {
+                       macStr = fields[4][len(fields[4])-17:]
+               }
+
+               if macStr != hwaddr {
+                       continue
+               }
+
+               // Parse the IP
+               addr := api.InstanceStateNetworkAddress{
+                       Address: fields[2],
+                       Scope:   "global",
+               }
+
+               ip := net.ParseIP(addr.Address)
+               if ip == nil {
+                       continue
+               }
+
+               if ip.To4() != nil {
+                       addr.Family = "inet"
+
+                       _, subnet, _ := 
net.ParseCIDR(dbInfo.Config()["ipv4.address"])
+                       if subnet != nil {
+                               mask, _ := subnet.Mask.Size()
+                               addr.Netmask = fmt.Sprintf("%d", mask)
+                       }
+               } else {
+                       addr.Family = "inet6"
+
+                       _, subnet, _ := 
net.ParseCIDR(dbInfo.Config()["ipv6.address"])
+                       if subnet != nil {
+                               mask, _ := subnet.Mask.Size()
+                               addr.Netmask = fmt.Sprintf("%d", mask)
+                       }
+               }
+
+               addresses = append(addresses, addr)
+       }
+
+       return addresses, nil
+}
+
 // The network structs and functions
 func networkLoadByName(s *state.State, name string) (*network, error) {
        id, dbInfo, err := s.Cluster.NetworkGet(name)
diff --git a/lxd/vm_qemu.go b/lxd/vm_qemu.go
index 00bf6366c0..19781a3d2f 100644
--- a/lxd/vm_qemu.go
+++ b/lxd/vm_qemu.go
@@ -6,6 +6,7 @@ import (
        "fmt"
        "io"
        "io/ioutil"
+       "net"
        "net/http"
        "os"
        "os/exec"
@@ -2376,13 +2377,61 @@ func (vm *vmQemu) RenderState() (*api.InstanceState, 
error) {
                status, err := vm.agentGetState()
                if err != nil {
                        logger.Warn("Could not get VM state from agent", 
log.Ctx{"project": vm.Project(), "instance": vm.Name(), "err": err})
-               } else {
-                       status.Pid = int64(pid)
-                       status.Status = statusCode.String()
-                       status.StatusCode = statusCode
+                       status = &api.InstanceState{}
+                       status.Processes = -1
+
+                       networks := map[string]api.InstanceStateNetwork{}
+                       for k, m := range vm.ExpandedDevices() {
+                               // We only care about nics.
+                               if m["type"] != "nic" || m["nictype"] != 
"bridged" {
+                                       continue
+                               }
+
+                               // Fill the MAC address.
+                               m, err := vm.fillNetworkDevice(k, m)
+                               if err != nil {
+                                       return nil, err
+                               }
+
+                               // Parse the lease file.
+                               addresses, err := 
networkGetLeaseAddresses(vm.state, m["parent"], m["hwaddr"])
+                               if err != nil {
+                                       return nil, err
+                               }
+
+                               if len(addresses) == 0 {
+                                       continue
+                               }
 
-                       return status, nil
+                               // Get MTU.
+                               iface, err := net.InterfaceByName(m["parent"])
+                               if err != nil {
+                                       return nil, err
+                               }
+
+                               if m["host_name"] == "" {
+                                       m["host_name"] = 
vm.localConfig[fmt.Sprintf("volatile.%s.host_name", k)]
+                               }
+
+                               networks[k] = api.InstanceStateNetwork{
+                                       Addresses: addresses,
+                                       Counters:  
api.InstanceStateNetworkCounters(shared.NetworkGetCounters(m["host_name"])),
+                                       Hwaddr:    m["hwaddr"],
+                                       HostName:  m["host_name"],
+                                       Mtu:       iface.MTU,
+                                       State:     "up",
+                                       Type:      "broadcast",
+                               }
+                       }
+
+                       status.Network = networks
                }
+
+               status.Pid = int64(pid)
+               status.Status = statusCode.String()
+               status.StatusCode = statusCode
+
+               return status, nil
        }
 
        // At least return the Status and StatusCode if we couldn't get any
_______________________________________________
lxc-devel mailing list
lxc-devel@lists.linuxcontainers.org
http://lists.linuxcontainers.org/listinfo/lxc-devel

Reply via email to