runconfig/config.go
6393c383
 package runconfig
 
 import (
767df67e
 	"encoding/json"
a7e686a7
 	"fmt"
767df67e
 	"io"
 
a7e686a7
 	"github.com/docker/docker/volume"
907407d0
 	"github.com/docker/engine-api/types/container"
2bb3fc1b
 	networktypes "github.com/docker/engine-api/types/network"
6393c383
 )
 
4ce81779
 // DecodeContainerConfig decodes a json encoded config into a ContainerConfigWrapper
 // struct and returns both a Config and an HostConfig struct
 // Be aware this function is not checking whether the resulted structs are nil,
 // it's your business to do so
2bb3fc1b
 func DecodeContainerConfig(src io.Reader) (*container.Config, *container.HostConfig, *networktypes.NetworkingConfig, error) {
767df67e
 	var w ContainerConfigWrapper
a7e686a7
 
 	decoder := json.NewDecoder(src)
767df67e
 	if err := decoder.Decode(&w); err != nil {
2bb3fc1b
 		return nil, nil, nil, err
6393c383
 	}
767df67e
 
f6ed5905
 	hc := w.getHostConfig()
 
a7e686a7
 	// Perform platform-specific processing of Volumes and Binds.
 	if w.Config != nil && hc != nil {
 
927b334e
 		// Initialize the volumes map if currently nil
a7e686a7
 		if w.Config.Volumes == nil {
 			w.Config.Volumes = make(map[string]struct{})
 		}
 
 		// Now validate all the volumes and binds
 		if err := validateVolumesAndBindSettings(w.Config, hc); err != nil {
2bb3fc1b
 			return nil, nil, nil, err
a7e686a7
 		}
 	}
 
f6ed5905
 	// Certain parameters need daemon-side validation that cannot be done
 	// on the client, as only the daemon knows what is valid for the platform.
 	if err := ValidateNetMode(w.Config, hc); err != nil {
2bb3fc1b
 		return nil, nil, nil, err
f6ed5905
 	}
 
15e35c44
 	// Validate the isolation level
 	if err := ValidateIsolationLevel(hc); err != nil {
2bb3fc1b
 		return nil, nil, nil, err
15e35c44
 	}
2bb3fc1b
 	return w.Config, hc, w.NetworkingConfig, nil
6393c383
 }
a7e686a7
 
 // validateVolumesAndBindSettings validates each of the volumes and bind settings
 // passed by the caller to ensure they are valid.
7ac4232e
 func validateVolumesAndBindSettings(c *container.Config, hc *container.HostConfig) error {
a7e686a7
 
 	// Ensure all volumes and binds are valid.
 	for spec := range c.Volumes {
 		if _, err := volume.ParseMountSpec(spec, hc.VolumeDriver); err != nil {
 			return fmt.Errorf("Invalid volume spec %q: %v", spec, err)
 		}
 	}
 	for _, spec := range hc.Binds {
 		if _, err := volume.ParseMountSpec(spec, hc.VolumeDriver); err != nil {
 			return fmt.Errorf("Invalid bind mount spec %q: %v", spec, err)
 		}
 	}
 
 	return nil
 }