Browse code

Decouple daemon and container to pause and unpause containers.

Signed-off-by: David Calavera <david.calavera@gmail.com>

David Calavera authored on 2015/11/03 08:39:39
Showing 5 changed files
... ...
@@ -22,8 +22,8 @@ type ContainerCommitConfig struct {
22 22
 // The image can optionally be tagged into a repository.
23 23
 func (daemon *Daemon) Commit(container *Container, c *ContainerCommitConfig) (*image.Image, error) {
24 24
 	if c.Pause && !container.isPaused() {
25
-		container.pause()
26
-		defer container.unpause()
25
+		daemon.containerPause(container)
26
+		defer daemon.containerUnpause(container)
27 27
 	}
28 28
 
29 29
 	rwTar, err := daemon.exportContainerRw(container)
... ...
@@ -343,50 +343,6 @@ func (container *Container) ExitOnNext() {
343 343
 	container.monitor.ExitOnNext()
344 344
 }
345 345
 
346
-func (container *Container) pause() error {
347
-	container.Lock()
348
-	defer container.Unlock()
349
-
350
-	// We cannot Pause the container which is not running
351
-	if !container.Running {
352
-		return derr.ErrorCodeNotRunning.WithArgs(container.ID)
353
-	}
354
-
355
-	// We cannot Pause the container which is already paused
356
-	if container.Paused {
357
-		return derr.ErrorCodeAlreadyPaused.WithArgs(container.ID)
358
-	}
359
-
360
-	if err := container.daemon.execDriver.Pause(container.command); err != nil {
361
-		return err
362
-	}
363
-	container.Paused = true
364
-	container.logEvent("pause")
365
-	return nil
366
-}
367
-
368
-func (container *Container) unpause() error {
369
-	container.Lock()
370
-	defer container.Unlock()
371
-
372
-	// We cannot unpause the container which is not running
373
-	if !container.Running {
374
-		return derr.ErrorCodeNotRunning.WithArgs(container.ID)
375
-	}
376
-
377
-	// We cannot unpause the container which is not paused
378
-	if !container.Paused {
379
-		return derr.ErrorCodeNotPaused.WithArgs(container.ID)
380
-	}
381
-
382
-	if err := container.daemon.execDriver.Unpause(container.command); err != nil {
383
-		return err
384
-	}
385
-	container.Paused = false
386
-	container.logEvent("unpause")
387
-	return nil
388
-}
389
-
390 346
 // Resize changes the TTY of the process running inside the container
391 347
 // to the given height and width. The container must be running.
392 348
 func (container *Container) Resize(h, w int) error {
... ...
@@ -849,10 +849,10 @@ func (daemon *Daemon) shutdownContainer(c *Container) error {
849 849
 		if !ok {
850 850
 			return fmt.Errorf("System doesn not support SIGTERM")
851 851
 		}
852
-		if err := c.daemon.kill(c, int(sig)); err != nil {
852
+		if err := daemon.kill(c, int(sig)); err != nil {
853 853
 			return fmt.Errorf("sending SIGTERM to container %s with error: %v", c.ID, err)
854 854
 		}
855
-		if err := c.unpause(); err != nil {
855
+		if err := daemon.containerUnpause(c); err != nil {
856 856
 			return fmt.Errorf("Failed to unpause container %s with error: %v", c.ID, err)
857 857
 		}
858 858
 		if _, err := c.WaitStop(10 * time.Second); err != nil {
... ...
@@ -861,7 +861,7 @@ func (daemon *Daemon) shutdownContainer(c *Container) error {
861 861
 			if !ok {
862 862
 				return fmt.Errorf("System does not support SIGKILL")
863 863
 			}
864
-			if err := c.daemon.kill(c, int(sig)); err != nil {
864
+			if err := daemon.kill(c, int(sig)); err != nil {
865 865
 				logrus.Errorf("Failed to SIGKILL container %s", c.ID)
866 866
 			}
867 867
 			c.WaitStop(-1 * time.Second)
... ...
@@ -11,9 +11,33 @@ func (daemon *Daemon) ContainerPause(name string) error {
11 11
 		return err
12 12
 	}
13 13
 
14
-	if err := container.pause(); err != nil {
14
+	if err := daemon.containerPause(container); err != nil {
15 15
 		return derr.ErrorCodePauseError.WithArgs(name, err)
16 16
 	}
17 17
 
18 18
 	return nil
19 19
 }
20
+
21
+// containerPause pauses the container execution without stopping the process.
22
+// The execution can be resumed by calling containerUnpause.
23
+func (daemon *Daemon) containerPause(container *Container) error {
24
+	container.Lock()
25
+	defer container.Unlock()
26
+
27
+	// We cannot Pause the container which is not running
28
+	if !container.Running {
29
+		return derr.ErrorCodeNotRunning.WithArgs(container.ID)
30
+	}
31
+
32
+	// We cannot Pause the container which is already paused
33
+	if container.Paused {
34
+		return derr.ErrorCodeAlreadyPaused.WithArgs(container.ID)
35
+	}
36
+
37
+	if err := daemon.execDriver.Pause(container.command); err != nil {
38
+		return err
39
+	}
40
+	container.Paused = true
41
+	daemon.logContainerEvent(container, "pause")
42
+	return nil
43
+}
... ...
@@ -11,9 +11,33 @@ func (daemon *Daemon) ContainerUnpause(name string) error {
11 11
 		return err
12 12
 	}
13 13
 
14
-	if err := container.unpause(); err != nil {
14
+	if err := daemon.containerUnpause(container); err != nil {
15 15
 		return derr.ErrorCodeCantUnpause.WithArgs(name, err)
16 16
 	}
17 17
 
18 18
 	return nil
19 19
 }
20
+
21
+// containerUnpause resumes the container execution after the container is paused.
22
+func (daemon *Daemon) containerUnpause(container *Container) error {
23
+	container.Lock()
24
+	defer container.Unlock()
25
+
26
+	// We cannot unpause the container which is not running
27
+	if !container.Running {
28
+		return derr.ErrorCodeNotRunning.WithArgs(container.ID)
29
+	}
30
+
31
+	// We cannot unpause the container which is not paused
32
+	if !container.Paused {
33
+		return derr.ErrorCodeNotPaused.WithArgs(container.ID)
34
+	}
35
+
36
+	if err := daemon.execDriver.Unpause(container.command); err != nil {
37
+		return err
38
+	}
39
+
40
+	container.Paused = false
41
+	daemon.logContainerEvent(container, "unpause")
42
+	return nil
43
+}