1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128
|
// -*- Mode: Go; indent-tabs-mode: t -*-
/*
* Copyright (C) 2019 Canonical Ltd
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 3 as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
*/
package builtin
/*
* Multipass is a tool to create and manage Virtual Machines and their images.
* Each VM runs as a separate "qemu" process (on Linux). VM images are automatically
* downloaded, but need conversion using "qemu-img". Networking is provided by
* configuring a TUN/TAP network on the host, with DHCP provided by a shared
* "dnsmasq" process. File sharing between the VM and the host is provided by a
* "sshfs_server" utility. All these utilities are shipped in the snap.
*
* Each of these utilities have a different purpose, and an attempt
* to confine them all in a single profile would result in an extremely broad AppArmor
* profile.
*
* Instead we defer to Multipass the responsibility of generating custom AppArmor
* profiles for each of these utilities, and trust it launches each utility with
* all possible security mechanisms enabled. The Multipass daemon itself will run
* under this restricted policy.
*/
const multipassSupportSummary = `allows operating as the Multipass service`
const multipassSupportBaseDeclarationPlugs = `
multipass-support:
allow-installation: false
deny-auto-connection: true
`
const multipassSupportBaseDeclarationSlots = `
multipass-support:
allow-installation:
slot-snap-type:
- core
deny-auto-connection: true
`
const multipassSupportConnectedPlugAppArmor = `
# Description: this policy intentionally allows the Multipass daemon to configure AppArmor
# as Multipass generates AppArmor profiles for the utility processes it spawns.
/sbin/apparmor_parser ixr,
/etc/apparmor{,.d}/{,**} r,
/sys/kernel/security/apparmor/{,**} r,
/sys/kernel/security/apparmor/.remove w,
/sys/kernel/security/apparmor/.replace w,
# Allow running utility processes under the specialized AppArmor profiles.
# These profiles will prevent utility processes escaping confinement.
capability mac_admin,
# Multipass has a server/client design, using a socket for IPC. The daemon runs
# as root, but makes the socket accessible to anyone in the sudo group.
capability chown,
# Multipass will also use privilege separation when running utility processes
capability setuid,
capability setgid,
# Some utility process (e.g. dnsmasq) will drop root privileges after startup and
# change to another user. The Multipass daemon needs ability to stop them.
capability kill,
# Profiles Multipass generates have a naming scheme, restrict any profile changes to
# those matching that scheme. Need unsafe to prevent env scrubbing.
change_profile unsafe /var/snap/{@{SNAP_NAME},@{SNAP_INSTANCE_NAME}}/usr/bin/* -> multipass.*,
signal (send) peer=multipass.*,
ptrace (read, trace) peer=multipass.*,
`
const multipassSupportConnectedPlugSecComp = `
# Description: allow operating as the Multipass daemon, and enable its various utilites
# (qemu, qemu-img, dnsmasq, sshfs_server)
# Note that this profile necessarily contains the union of all the syscalls each of the
# utilities requires. We rely on Multipass to generate specific AppArmor profiles
# for each child process, to further restrict their abilities.
# dnsmasq fails unless it can drop supplementary groups
setgroups 0 -
setgroups32 0 -
# Multipassd will have a child process - sshfs_server - which allows mounting a
# user-specified directory on the host into the VM. Here we permit typical filesytem
# syscalls with the knowledge that Multipass will generate a specific AppArmor
# profile for sshfs_server, restricting any filesystem access to just the
# user-specified directory.
# More filesystem syscalls sshfs_server will need, as it allows user to change
# file owner/group arbitrarily.
chown
chown32
fchown
fchown32
fchownat
lchown
lchownat
`
func init() {
registerIface(&commonInterface{
name: "multipass-support",
summary: multipassSupportSummary,
implicitOnCore: true,
implicitOnClassic: true,
baseDeclarationSlots: multipassSupportBaseDeclarationSlots,
baseDeclarationPlugs: multipassSupportBaseDeclarationPlugs,
connectedPlugAppArmor: multipassSupportConnectedPlugAppArmor,
connectedPlugSecComp: multipassSupportConnectedPlugSecComp,
})
}
|