lcow: Allow the client to add device cgroup rules
Signed-off-by: John Starks <jostarks@microsoft.com>
This commit is contained in:
parent
349aeeab7c
commit
e9268d9642
3 changed files with 56 additions and 39 deletions
|
@ -1,11 +1,20 @@
|
|||
package daemon // import "github.com/docker/docker/daemon"
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"regexp"
|
||||
"strconv"
|
||||
|
||||
"github.com/docker/docker/container"
|
||||
"github.com/docker/docker/daemon/caps"
|
||||
specs "github.com/opencontainers/runtime-spec/specs-go"
|
||||
)
|
||||
|
||||
// nolint: gosimple
|
||||
var (
|
||||
deviceCgroupRuleRegex = regexp.MustCompile("^([acb]) ([0-9]+|\\*):([0-9]+|\\*) ([rwm]{1,3})$")
|
||||
)
|
||||
|
||||
func setCapabilities(s *specs.Spec, c *container.Container) error {
|
||||
var caplist []string
|
||||
var err error
|
||||
|
@ -29,3 +38,41 @@ func setCapabilities(s *specs.Spec, c *container.Container) error {
|
|||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func appendDevicePermissionsFromCgroupRules(devPermissions []specs.LinuxDeviceCgroup, rules []string) ([]specs.LinuxDeviceCgroup, error) {
|
||||
for _, deviceCgroupRule := range rules {
|
||||
ss := deviceCgroupRuleRegex.FindAllStringSubmatch(deviceCgroupRule, -1)
|
||||
if len(ss[0]) != 5 {
|
||||
return nil, fmt.Errorf("invalid device cgroup rule format: '%s'", deviceCgroupRule)
|
||||
}
|
||||
matches := ss[0]
|
||||
|
||||
dPermissions := specs.LinuxDeviceCgroup{
|
||||
Allow: true,
|
||||
Type: matches[1],
|
||||
Access: matches[4],
|
||||
}
|
||||
if matches[2] == "*" {
|
||||
major := int64(-1)
|
||||
dPermissions.Major = &major
|
||||
} else {
|
||||
major, err := strconv.ParseInt(matches[2], 10, 64)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("invalid major value in device cgroup rule format: '%s'", deviceCgroupRule)
|
||||
}
|
||||
dPermissions.Major = &major
|
||||
}
|
||||
if matches[3] == "*" {
|
||||
minor := int64(-1)
|
||||
dPermissions.Minor = &minor
|
||||
} else {
|
||||
minor, err := strconv.ParseInt(matches[3], 10, 64)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("invalid minor value in device cgroup rule format: '%s'", deviceCgroupRule)
|
||||
}
|
||||
dPermissions.Minor = &minor
|
||||
}
|
||||
devPermissions = append(devPermissions, dPermissions)
|
||||
}
|
||||
return devPermissions, nil
|
||||
}
|
||||
|
|
|
@ -6,7 +6,6 @@ import (
|
|||
"os"
|
||||
"os/exec"
|
||||
"path/filepath"
|
||||
"regexp"
|
||||
"sort"
|
||||
"strconv"
|
||||
"strings"
|
||||
|
@ -28,11 +27,6 @@ import (
|
|||
"golang.org/x/sys/unix"
|
||||
)
|
||||
|
||||
// nolint: gosimple
|
||||
var (
|
||||
deviceCgroupRuleRegex = regexp.MustCompile("^([acb]) ([0-9]+|\\*):([0-9]+|\\*) ([rwm]{1,3})$")
|
||||
)
|
||||
|
||||
func setResources(s *specs.Spec, r containertypes.Resources) error {
|
||||
weightDevices, err := getBlkioWeightDevices(r)
|
||||
if err != nil {
|
||||
|
@ -114,39 +108,10 @@ func setDevices(s *specs.Spec, c *container.Container) error {
|
|||
devPermissions = append(devPermissions, dPermissions...)
|
||||
}
|
||||
|
||||
for _, deviceCgroupRule := range c.HostConfig.DeviceCgroupRules {
|
||||
ss := deviceCgroupRuleRegex.FindAllStringSubmatch(deviceCgroupRule, -1)
|
||||
if len(ss[0]) != 5 {
|
||||
return fmt.Errorf("invalid device cgroup rule format: '%s'", deviceCgroupRule)
|
||||
}
|
||||
matches := ss[0]
|
||||
|
||||
dPermissions := specs.LinuxDeviceCgroup{
|
||||
Allow: true,
|
||||
Type: matches[1],
|
||||
Access: matches[4],
|
||||
}
|
||||
if matches[2] == "*" {
|
||||
major := int64(-1)
|
||||
dPermissions.Major = &major
|
||||
} else {
|
||||
major, err := strconv.ParseInt(matches[2], 10, 64)
|
||||
if err != nil {
|
||||
return fmt.Errorf("invalid major value in device cgroup rule format: '%s'", deviceCgroupRule)
|
||||
}
|
||||
dPermissions.Major = &major
|
||||
}
|
||||
if matches[3] == "*" {
|
||||
minor := int64(-1)
|
||||
dPermissions.Minor = &minor
|
||||
} else {
|
||||
minor, err := strconv.ParseInt(matches[3], 10, 64)
|
||||
if err != nil {
|
||||
return fmt.Errorf("invalid minor value in device cgroup rule format: '%s'", deviceCgroupRule)
|
||||
}
|
||||
dPermissions.Minor = &minor
|
||||
}
|
||||
devPermissions = append(devPermissions, dPermissions)
|
||||
var err error
|
||||
devPermissions, err = appendDevicePermissionsFromCgroupRules(devPermissions, c.HostConfig.DeviceCgroupRules)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -347,6 +347,11 @@ func (daemon *Daemon) createSpecLinuxFields(c *container.Container, s *specs.Spe
|
|||
if err := setCapabilities(s, c); err != nil {
|
||||
return fmt.Errorf("linux spec capabilities: %v", err)
|
||||
}
|
||||
devPermissions, err := appendDevicePermissionsFromCgroupRules(nil, c.HostConfig.DeviceCgroupRules)
|
||||
if err != nil {
|
||||
return fmt.Errorf("linux runtime spec devices: %v", err)
|
||||
}
|
||||
s.Linux.Resources.Devices = devPermissions
|
||||
return nil
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue