start.go 1.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475
  1. package daemon
  2. import (
  3. "fmt"
  4. "os"
  5. "strings"
  6. "github.com/docker/docker/engine"
  7. "github.com/docker/docker/runconfig"
  8. )
  9. func (daemon *Daemon) ContainerStart(job *engine.Job) engine.Status {
  10. if len(job.Args) < 1 {
  11. return job.Errorf("Usage: %s container_id", job.Name)
  12. }
  13. var (
  14. name = job.Args[0]
  15. container = daemon.Get(name)
  16. )
  17. if container == nil {
  18. return job.Errorf("No such container: %s", name)
  19. }
  20. if container.IsRunning() {
  21. return job.Errorf("Container already started")
  22. }
  23. // If no environment was set, then no hostconfig was passed.
  24. // This is kept for backward compatibility - hostconfig should be passed when
  25. // creating a container, not during start.
  26. if len(job.Environ()) > 0 {
  27. hostConfig := runconfig.ContainerHostConfigFromJob(job)
  28. if err := daemon.setHostConfig(container, hostConfig); err != nil {
  29. return job.Error(err)
  30. }
  31. }
  32. if err := container.Start(); err != nil {
  33. container.LogEvent("die")
  34. return job.Errorf("Cannot start container %s: %s", name, err)
  35. }
  36. return engine.StatusOK
  37. }
  38. func (daemon *Daemon) setHostConfig(container *Container, hostConfig *runconfig.HostConfig) error {
  39. container.Lock()
  40. defer container.Unlock()
  41. if err := parseSecurityOpt(container, hostConfig); err != nil {
  42. return err
  43. }
  44. // Validate the HostConfig binds. Make sure that:
  45. // the source exists
  46. for _, bind := range hostConfig.Binds {
  47. splitBind := strings.Split(bind, ":")
  48. source := splitBind[0]
  49. // ensure the source exists on the host
  50. _, err := os.Stat(source)
  51. if err != nil && os.IsNotExist(err) {
  52. err = os.MkdirAll(source, 0755)
  53. if err != nil {
  54. return fmt.Errorf("Could not create local directory '%s' for bind mount: %s!", source, err.Error())
  55. }
  56. }
  57. }
  58. // Register any links from the host config before starting the container
  59. if err := daemon.RegisterLinks(container, hostConfig); err != nil {
  60. return err
  61. }
  62. container.hostConfig = hostConfig
  63. container.toDisk()
  64. return nil
  65. }