Browse code

Merge remote-tracking branch 'dotcloud/master' into dhrp/docs

Conflicts:
docker/docker.go
docs/sources/installation/archlinux.rst
docs/sources/installation/index.rst
docs/sources/installation/ubuntulinux.rst
runtime.go
utils.go

Thatcher Peskens authored on 2013/04/23 10:44:50
Showing 8 changed files
... ...
@@ -150,6 +150,82 @@ func TestMultipleAttachRestart(t *testing.T) {
150 150
 	}
151 151
 }
152 152
 
153
+func TestDiff(t *testing.T) {
154
+	runtime, err := newTestRuntime()
155
+	if err != nil {
156
+		t.Fatal(err)
157
+	}
158
+	defer nuke(runtime)
159
+
160
+	// Create a container and remove a file
161
+	container1, err := runtime.Create(
162
+		&Config{
163
+			Image: GetTestImage(runtime).Id,
164
+			Cmd:   []string{"/bin/rm", "/etc/passwd"},
165
+		},
166
+	)
167
+	if err != nil {
168
+		t.Fatal(err)
169
+	}
170
+	defer runtime.Destroy(container1)
171
+
172
+	if err := container1.Run(); err != nil {
173
+		t.Fatal(err)
174
+	}
175
+
176
+	// Check the changelog
177
+	c, err := container1.Changes()
178
+	if err != nil {
179
+		t.Fatal(err)
180
+	}
181
+	success := false
182
+	for _, elem := range c {
183
+		if elem.Path == "/etc/passwd" && elem.Kind == 2 {
184
+			success = true
185
+		}
186
+	}
187
+	if !success {
188
+		t.Fatalf("/etc/passwd as been removed but is not present in the diff")
189
+	}
190
+
191
+	// Commit the container
192
+	rwTar, err := container1.ExportRw()
193
+	if err != nil {
194
+		t.Error(err)
195
+	}
196
+	img, err := runtime.graph.Create(rwTar, container1, "unit test commited image - diff", "")
197
+	if err != nil {
198
+		t.Error(err)
199
+	}
200
+
201
+	// Create a new container from the commited image
202
+	container2, err := runtime.Create(
203
+		&Config{
204
+			Image: img.Id,
205
+			Cmd:   []string{"cat", "/etc/passwd"},
206
+		},
207
+	)
208
+	if err != nil {
209
+		t.Fatal(err)
210
+	}
211
+	defer runtime.Destroy(container2)
212
+
213
+	if err := container2.Run(); err != nil {
214
+		t.Fatal(err)
215
+	}
216
+
217
+	// Check the changelog
218
+	c, err = container2.Changes()
219
+	if err != nil {
220
+		t.Fatal(err)
221
+	}
222
+	for _, elem := range c {
223
+		if elem.Path == "/etc/passwd" {
224
+			t.Fatalf("/etc/passwd should not be present in the diff after commit.")
225
+		}
226
+	}
227
+}
228
+
153 229
 func TestCommitRun(t *testing.T) {
154 230
 	runtime, err := newTestRuntime()
155 231
 	if err != nil {
... ...
@@ -7,9 +7,11 @@ import (
7 7
 	"github.com/dotcloud/docker/rcli"
8 8
 	"github.com/dotcloud/docker/term"
9 9
 	"io"
10
+	"io/ioutil"
10 11
 	"log"
11 12
 	"os"
12 13
 	"os/signal"
14
+	"strconv"
13 15
 	"syscall"
14 16
 )
15 17
 
... ...
@@ -54,8 +56,13 @@ func main() {
54 54
 }
55 55
 
56 56
 func createPidFile(pidfile string) error {
57
-	if _, err := os.Stat(pidfile); err == nil {
58
-		return fmt.Errorf("pid file found, ensure docker is not running or delete %s", pidfile)
57
+	if pidString, err := ioutil.ReadFile(pidfile); err == nil {
58
+		pid, err := strconv.Atoi(string(pidString))
59
+		if err == nil {
60
+			if _, err := os.Stat(fmt.Sprintf("/proc/%d/", pid)); err == nil {
61
+				return fmt.Errorf("pid file found, ensure docker is not running or delete %s", pidfile)
62
+			}
63
+		}
59 64
 	}
60 65
 
61 66
 	file, err := os.Create(pidfile)
... ...
@@ -56,7 +56,10 @@ There is a systemd service unit created for docker.  To start the docker service
56 56
 
57 57
     sudo systemctl start docker
58 58
 
59
+<<<<<<< HEAD
59 60
 
61
+=======
62
+>>>>>>> dotcloud/master
60 63
 To start on system boot:
61 64
 
62 65
 ::
63 66
new file mode 100644
... ...
@@ -0,0 +1,9 @@
0
+package docker
1
+
2
+import (
3
+	"fmt"
4
+)
5
+
6
+func getKernelVersion() (*KernelVersionInfo, error) {
7
+	return nil, fmt.Errorf("Kernel version detection is not available on darwin")
8
+}
0 9
new file mode 100644
... ...
@@ -0,0 +1,69 @@
0
+package docker
1
+
2
+import (
3
+	"bytes"
4
+	"strconv"
5
+	"strings"
6
+	"syscall"
7
+)
8
+
9
+func getKernelVersion() (*KernelVersionInfo, error) {
10
+	var (
11
+		uts                  syscall.Utsname
12
+		flavor               string
13
+		kernel, major, minor int
14
+		err                  error
15
+	)
16
+
17
+	if err := syscall.Uname(&uts); err != nil {
18
+		return nil, err
19
+	}
20
+
21
+	release := make([]byte, len(uts.Release))
22
+
23
+	i := 0
24
+	for _, c := range uts.Release {
25
+		release[i] = byte(c)
26
+		i++
27
+	}
28
+
29
+	// Remove the \x00 from the release for Atoi to parse correctly
30
+	release = release[:bytes.IndexByte(release, 0)]
31
+
32
+	tmp := strings.SplitN(string(release), "-", 2)
33
+	tmp2 := strings.SplitN(tmp[0], ".", 3)
34
+
35
+	if len(tmp2) > 0 {
36
+		kernel, err = strconv.Atoi(tmp2[0])
37
+		if err != nil {
38
+			return nil, err
39
+		}
40
+	}
41
+
42
+	if len(tmp2) > 1 {
43
+		major, err = strconv.Atoi(tmp2[1])
44
+		if err != nil {
45
+			return nil, err
46
+		}
47
+	}
48
+
49
+	if len(tmp2) > 2 {
50
+		minor, err = strconv.Atoi(tmp2[2])
51
+		if err != nil {
52
+			return nil, err
53
+		}
54
+	}
55
+
56
+	if len(tmp) == 2 {
57
+		flavor = tmp[1]
58
+	} else {
59
+		flavor = ""
60
+	}
61
+
62
+	return &KernelVersionInfo{
63
+		Kernel: kernel,
64
+		Major:  major,
65
+		Minor:  minor,
66
+		Flavor: flavor,
67
+	}, nil
68
+}
... ...
@@ -92,7 +92,7 @@ func MountAUFS(ro []string, rw string, target string) error {
92 92
 	rwBranch := fmt.Sprintf("%v=rw", rw)
93 93
 	roBranches := ""
94 94
 	for _, layer := range ro {
95
-		roBranches += fmt.Sprintf("%v=ro:", layer)
95
+		roBranches += fmt.Sprintf("%v=ro+wh:", layer)
96 96
 	}
97 97
 	branches := fmt.Sprintf("br:%v:%v", rwBranch, roBranches)
98 98
 
... ...
@@ -136,34 +136,9 @@ func (image *Image) Mount(root, rw string) error {
136 136
 	if err := os.Mkdir(rw, 0755); err != nil && !os.IsExist(err) {
137 137
 		return err
138 138
 	}
139
-	// FIXME: @creack shouldn't we do this after going over changes?
140 139
 	if err := MountAUFS(layers, rw, root); err != nil {
141 140
 		return err
142 141
 	}
143
-	// FIXME: Create tests for deletion
144
-	// FIXME: move this part to change.go
145
-	// Retrieve the changeset from the parent and apply it to the container
146
-	//  - Retrieve the changes
147
-	changes, err := Changes(layers, layers[0])
148
-	if err != nil {
149
-		return err
150
-	}
151
-	// Iterate on changes
152
-	for _, c := range changes {
153
-		// If there is a delete
154
-		if c.Kind == ChangeDelete {
155
-			// Make sure the directory exists
156
-			file_path, file_name := path.Dir(c.Path), path.Base(c.Path)
157
-			if err := os.MkdirAll(path.Join(rw, file_path), 0755); err != nil {
158
-				return err
159
-			}
160
-			// And create the whiteout (we just need to create empty file, discard the return)
161
-			if _, err := os.Create(path.Join(path.Join(rw, file_path),
162
-				".wh."+path.Base(file_name))); err != nil {
163
-				return err
164
-			}
165
-		}
166
-	}
167 142
 	return nil
168 143
 }
169 144
 
... ...
@@ -295,14 +295,13 @@ func NewRuntime() (*Runtime, error) {
295 295
 		return nil, err
296 296
 	}
297 297
 
298
-	k, err := GetKernelVersion()
299
-	if err != nil {
300
-		return nil, err
301
-	}
302
-	runtime.kernelVersion = k
303
-
304
-	if CompareKernelVersion(k, &KernelVersionInfo{Kernel: 3, Major: 8, Minor: 0}) < 0 {
305
-		log.Printf("WARNING: You are running linux kernel version %s, which might be unstable running docker. Please upgrade your kernel to 3.8.0.", k.String())
298
+	if k, err := GetKernelVersion(); err != nil {
299
+		log.Printf("WARNING: %s\n", err)
300
+	} else {
301
+		runtime.kernelVersion = k
302
+		if CompareKernelVersion(k, &KernelVersionInfo{Kernel: 3, Major: 8, Minor: 0}) < 0 {
303
+			log.Printf("WARNING: You are running linux kernel version %s, which might be unstable running docker. Please upgrade your kernel to 3.8.0.", k.String())
304
+		}
306 305
 	}
307 306
 
308 307
 	if cgroupMemoryMountpoint, err := FindCgroupMountpoint("memory"); err != nil {
... ...
@@ -14,10 +14,8 @@ import (
14 14
 	"path/filepath"
15 15
 	"regexp"
16 16
 	"runtime"
17
-	"strconv"
18 17
 	"strings"
19 18
 	"sync"
20
-	"syscall"
21 19
 	"time"
22 20
 )
23 21
 
... ...
@@ -407,52 +405,7 @@ type KernelVersionInfo struct {
407 407
 
408 408
 // FIXME: this doens't build on Darwin
409 409
 func GetKernelVersion() (*KernelVersionInfo, error) {
410
-	var uts syscall.Utsname
411
-
412
-	if err := syscall.Uname(&uts); err != nil {
413
-		return nil, err
414
-	}
415
-
416
-	release := make([]byte, len(uts.Release))
417
-
418
-	i := 0
419
-	for _, c := range uts.Release {
420
-		release[i] = byte(c)
421
-		i++
422
-	}
423
-
424
-	tmp := strings.SplitN(string(release), "-", 2)
425
-	if len(tmp) != 2 {
426
-		return nil, fmt.Errorf("Unrecognized kernel version")
427
-	}
428
-	tmp2 := strings.SplitN(tmp[0], ".", 3)
429
-	if len(tmp2) != 3 {
430
-		return nil, fmt.Errorf("Unrecognized kernel version")
431
-	}
432
-
433
-	kernel, err := strconv.Atoi(tmp2[0])
434
-	if err != nil {
435
-		return nil, err
436
-	}
437
-
438
-	major, err := strconv.Atoi(tmp2[1])
439
-	if err != nil {
440
-		return nil, err
441
-	}
442
-
443
-	minor, err := strconv.Atoi(tmp2[2])
444
-	if err != nil {
445
-		return nil, err
446
-	}
447
-
448
-	flavor := tmp[1]
449
-
450
-	return &KernelVersionInfo{
451
-		Kernel: kernel,
452
-		Major:  major,
453
-		Minor:  minor,
454
-		Flavor: flavor,
455
-	}, nil
410
+	return getKernelVersion()
456 411
 }
457 412
 
458 413
 func (k *KernelVersionInfo) String() string {