diff options
Diffstat (limited to 'src/pkg/os/os_test.go')
-rw-r--r-- | src/pkg/os/os_test.go | 366 |
1 files changed, 183 insertions, 183 deletions
diff --git a/src/pkg/os/os_test.go b/src/pkg/os/os_test.go index 7ff2bddb3..4523cad79 100644 --- a/src/pkg/os/os_test.go +++ b/src/pkg/os/os_test.go @@ -5,13 +5,13 @@ package os_test import ( - "bytes"; - "fmt"; - "io"; - "io/ioutil"; - . "os"; - "strings"; - "testing"; + "bytes" + "fmt" + "io" + "io/ioutil" + . "os" + "strings" + "testing" ) var dot = []string{ @@ -34,16 +34,16 @@ var etc = []string{ } func size(name string, t *testing.T) uint64 { - file, err := Open(name, O_RDONLY, 0); - defer file.Close(); + file, err := Open(name, O_RDONLY, 0) + defer file.Close() if err != nil { t.Fatal("open failed:", err) } - var buf [100]byte; - len := 0; + var buf [100]byte + len := 0 for { - n, e := file.Read(&buf); - len += n; + n, e := file.Read(&buf) + len += n if e == EOF { break } @@ -51,68 +51,68 @@ func size(name string, t *testing.T) uint64 { t.Fatal("read failed:", err) } } - return uint64(len); + return uint64(len) } func TestStat(t *testing.T) { - dir, err := Stat("/etc/passwd"); + dir, err := Stat("/etc/passwd") if err != nil { t.Fatal("stat failed:", err) } if dir.Name != "passwd" { t.Error("name should be passwd; is", dir.Name) } - filesize := size("/etc/passwd", t); + filesize := size("/etc/passwd", t) if dir.Size != filesize { t.Error("size should be", filesize, "; is", dir.Size) } } func TestFstat(t *testing.T) { - file, err1 := Open("/etc/passwd", O_RDONLY, 0); - defer file.Close(); + file, err1 := Open("/etc/passwd", O_RDONLY, 0) + defer file.Close() if err1 != nil { t.Fatal("open failed:", err1) } - dir, err2 := file.Stat(); + dir, err2 := file.Stat() if err2 != nil { t.Fatal("fstat failed:", err2) } if dir.Name != "passwd" { t.Error("name should be passwd; is", dir.Name) } - filesize := size("/etc/passwd", t); + filesize := size("/etc/passwd", t) if dir.Size != filesize { t.Error("size should be", filesize, "; is", dir.Size) } } func TestLstat(t *testing.T) { - dir, err := Lstat("/etc/passwd"); + dir, err := Lstat("/etc/passwd") if err != nil { t.Fatal("lstat failed:", err) } if dir.Name != "passwd" { t.Error("name should be passwd; is", dir.Name) } - filesize := size("/etc/passwd", t); + filesize := size("/etc/passwd", t) if dir.Size != filesize { t.Error("size should be", filesize, "; is", dir.Size) } } func testReaddirnames(dir string, contents []string, t *testing.T) { - file, err := Open(dir, O_RDONLY, 0); - defer file.Close(); + file, err := Open(dir, O_RDONLY, 0) + defer file.Close() if err != nil { t.Fatalf("open %q failed: %v", dir, err) } - s, err2 := file.Readdirnames(-1); + s, err2 := file.Readdirnames(-1) if err2 != nil { t.Fatalf("readdirnames %q failed: %v", err2) } for _, m := range contents { - found := false; + found := false for _, n := range s { if n == "." || n == ".." { t.Errorf("got %s in directory", n) @@ -121,7 +121,7 @@ func testReaddirnames(dir string, contents []string, t *testing.T) { if found { t.Error("present twice:", m) } - found = true; + found = true } } if !found { @@ -131,23 +131,23 @@ func testReaddirnames(dir string, contents []string, t *testing.T) { } func testReaddir(dir string, contents []string, t *testing.T) { - file, err := Open(dir, O_RDONLY, 0); - defer file.Close(); + file, err := Open(dir, O_RDONLY, 0) + defer file.Close() if err != nil { t.Fatalf("open %q failed: %v", dir, err) } - s, err2 := file.Readdir(-1); + s, err2 := file.Readdir(-1) if err2 != nil { t.Fatalf("readdir %q failed: %v", dir, err2) } for _, m := range contents { - found := false; + found := false for _, n := range s { if m == n.Name { if found { t.Error("present twice:", m) } - found = true; + found = true } } if !found { @@ -157,51 +157,51 @@ func testReaddir(dir string, contents []string, t *testing.T) { } func TestReaddirnames(t *testing.T) { - testReaddirnames(".", dot, t); - testReaddirnames("/etc", etc, t); + testReaddirnames(".", dot, t) + testReaddirnames("/etc", etc, t) } func TestReaddir(t *testing.T) { - testReaddir(".", dot, t); - testReaddir("/etc", etc, t); + testReaddir(".", dot, t) + testReaddir("/etc", etc, t) } // Read the directory one entry at a time. func smallReaddirnames(file *File, length int, t *testing.T) []string { - names := make([]string, length); - count := 0; + names := make([]string, length) + count := 0 for { - d, err := file.Readdirnames(1); + d, err := file.Readdirnames(1) if err != nil { t.Fatalf("readdir %q failed: %v", file.Name(), err) } if len(d) == 0 { break } - names[count] = d[0]; - count++; + names[count] = d[0] + count++ } - return names[0:count]; + return names[0:count] } // Check that reading a directory one entry at a time gives the same result // as reading it all at once. func TestReaddirnamesOneAtATime(t *testing.T) { - dir := "/usr/bin"; // big directory that doesn't change often. - file, err := Open(dir, O_RDONLY, 0); - defer file.Close(); + dir := "/usr/bin" // big directory that doesn't change often. + file, err := Open(dir, O_RDONLY, 0) + defer file.Close() if err != nil { t.Fatalf("open %q failed: %v", dir, err) } - all, err1 := file.Readdirnames(-1); + all, err1 := file.Readdirnames(-1) if err1 != nil { t.Fatalf("readdirnames %q failed: %v", dir, err1) } - file1, err2 := Open(dir, O_RDONLY, 0); + file1, err2 := Open(dir, O_RDONLY, 0) if err2 != nil { t.Fatalf("open %q failed: %v", dir, err2) } - small := smallReaddirnames(file1, len(all)+100, t); // +100 in case we screw up + small := smallReaddirnames(file1, len(all)+100, t) // +100 in case we screw up for i, n := range all { if small[i] != n { t.Errorf("small read %q %q mismatch: %v", small[i], n) @@ -210,26 +210,26 @@ func TestReaddirnamesOneAtATime(t *testing.T) { } func TestHardLink(t *testing.T) { - from, to := "hardlinktestfrom", "hardlinktestto"; - Remove(from); // Just in case. - file, err := Open(to, O_CREAT|O_WRONLY, 0666); + from, to := "hardlinktestfrom", "hardlinktestto" + Remove(from) // Just in case. + file, err := Open(to, O_CREAT|O_WRONLY, 0666) if err != nil { t.Fatalf("open %q failed: %v", to, err) } - defer Remove(to); + defer Remove(to) if err = file.Close(); err != nil { t.Errorf("close %q failed: %v", to, err) } - err = Link(to, from); + err = Link(to, from) if err != nil { t.Fatalf("link %q, %q failed: %v", to, from, err) } - defer Remove(from); - tostat, err := Stat(to); + defer Remove(from) + tostat, err := Stat(to) if err != nil { t.Fatalf("stat %q failed: %v", to, err) } - fromstat, err := Stat(from); + fromstat, err := Stat(from) if err != nil { t.Fatalf("stat %q failed: %v", from, err) } @@ -239,74 +239,74 @@ func TestHardLink(t *testing.T) { } func TestSymLink(t *testing.T) { - from, to := "symlinktestfrom", "symlinktestto"; - Remove(from); // Just in case. - file, err := Open(to, O_CREAT|O_WRONLY, 0666); + from, to := "symlinktestfrom", "symlinktestto" + Remove(from) // Just in case. + file, err := Open(to, O_CREAT|O_WRONLY, 0666) if err != nil { t.Fatalf("open %q failed: %v", to, err) } - defer Remove(to); + defer Remove(to) if err = file.Close(); err != nil { t.Errorf("close %q failed: %v", to, err) } - err = Symlink(to, from); + err = Symlink(to, from) if err != nil { t.Fatalf("symlink %q, %q failed: %v", to, from, err) } - defer Remove(from); - tostat, err := Stat(to); + defer Remove(from) + tostat, err := Stat(to) if err != nil { t.Fatalf("stat %q failed: %v", to, err) } if tostat.FollowedSymlink { t.Fatalf("stat %q claims to have followed a symlink", to) } - fromstat, err := Stat(from); + fromstat, err := Stat(from) if err != nil { t.Fatalf("stat %q failed: %v", from, err) } if tostat.Dev != fromstat.Dev || tostat.Ino != fromstat.Ino { t.Errorf("symlink %q, %q did not create symlink", to, from) } - fromstat, err = Lstat(from); + fromstat, err = Lstat(from) if err != nil { t.Fatalf("lstat %q failed: %v", from, err) } if !fromstat.IsSymlink() { t.Fatalf("symlink %q, %q did not create symlink", to, from) } - fromstat, err = Stat(from); + fromstat, err = Stat(from) if err != nil { t.Fatalf("stat %q failed: %v", from, err) } if !fromstat.FollowedSymlink { t.Fatalf("stat %q did not follow symlink") } - s, err := Readlink(from); + s, err := Readlink(from) if err != nil { t.Fatalf("readlink %q failed: %v", from, err) } if s != to { t.Fatalf("after symlink %q != %q", s, to) } - file, err = Open(from, O_RDONLY, 0); + file, err = Open(from, O_RDONLY, 0) if err != nil { t.Fatalf("open %q failed: %v", from, err) } - file.Close(); + file.Close() } func TestLongSymlink(t *testing.T) { - s := "0123456789abcdef"; + s := "0123456789abcdef" // Long, but not too long: a common limit is 255. - s = s + s + s + s + s + s + s + s + s + s + s + s + s + s + s; - from := "longsymlinktestfrom"; - err := Symlink(s, from); + s = s + s + s + s + s + s + s + s + s + s + s + s + s + s + s + from := "longsymlinktestfrom" + err := Symlink(s, from) if err != nil { t.Fatalf("symlink %q, %q failed: %v", s, from, err) } - defer Remove(from); - r, err := Readlink(from); + defer Remove(from) + r, err := Readlink(from) if err != nil { t.Fatalf("readlink %q failed: %v", from, err) } @@ -316,49 +316,49 @@ func TestLongSymlink(t *testing.T) { } func TestRename(t *testing.T) { - from, to := "renamefrom", "renameto"; - Remove(to); // Just in case. - file, err := Open(from, O_CREAT|O_WRONLY, 0666); + from, to := "renamefrom", "renameto" + Remove(to) // Just in case. + file, err := Open(from, O_CREAT|O_WRONLY, 0666) if err != nil { t.Fatalf("open %q failed: %v", to, err) } if err = file.Close(); err != nil { t.Errorf("close %q failed: %v", to, err) } - err = Rename(from, to); + err = Rename(from, to) if err != nil { t.Fatalf("rename %q, %q failed: %v", to, from, err) } - defer Remove(to); - _, err = Stat(to); + defer Remove(to) + _, err = Stat(to) if err != nil { t.Errorf("stat %q failed: %v", to, err) } } func TestForkExec(t *testing.T) { - r, w, err := Pipe(); + r, w, err := Pipe() if err != nil { t.Fatalf("Pipe: %v", err) } - pid, err := ForkExec("/bin/pwd", []string{"pwd"}, nil, "/", []*File{nil, w, Stderr}); + pid, err := ForkExec("/bin/pwd", []string{"pwd"}, nil, "/", []*File{nil, w, Stderr}) if err != nil { t.Fatalf("ForkExec: %v", err) } - w.Close(); + w.Close() - var b bytes.Buffer; - io.Copy(&b, r); - output := b.String(); - expect := "/\n"; + var b bytes.Buffer + io.Copy(&b, r) + output := b.String() + expect := "/\n" if output != expect { t.Errorf("exec /bin/pwd returned %q wanted %q", output, expect) } - Wait(pid, 0); + Wait(pid, 0) } func checkMode(t *testing.T, path string, mode uint32) { - dir, err := Stat(path); + dir, err := Stat(path) if err != nil { t.Fatalf("Stat %q (looking for mode %#o): %s", path, mode, err) } @@ -368,9 +368,9 @@ func checkMode(t *testing.T, path string, mode uint32) { } func TestChmod(t *testing.T) { - MkdirAll("_obj", 0777); - const Path = "_obj/_TestChmod_"; - fd, err := Open(Path, O_WRONLY|O_CREAT, 0666); + MkdirAll("_obj", 0777) + const Path = "_obj/_TestChmod_" + fd, err := Open(Path, O_WRONLY|O_CREAT, 0666) if err != nil { t.Fatalf("create %s: %s", Path, err) } @@ -378,19 +378,19 @@ func TestChmod(t *testing.T) { if err = Chmod(Path, 0456); err != nil { t.Fatalf("chmod %s 0456: %s", Path, err) } - checkMode(t, Path, 0456); + checkMode(t, Path, 0456) if err = fd.Chmod(0123); err != nil { t.Fatalf("fchmod %s 0123: %s", Path, err) } - checkMode(t, Path, 0123); + checkMode(t, Path, 0123) - fd.Close(); - Remove(Path); + fd.Close() + Remove(Path) } func checkUidGid(t *testing.T, path string, uid, gid int) { - dir, err := Stat(path); + dir, err := Stat(path) if err != nil { t.Fatalf("Stat %q (looking for uid/gid %d/%d): %s", path, uid, gid, err) } @@ -408,49 +408,49 @@ func TestChown(t *testing.T) { // on the file. If _obj is on NFS, the Getgroups groups are // basically useless. - const Path = "/tmp/_TestChown_"; - fd, err := Open(Path, O_WRONLY|O_CREAT, 0666); + const Path = "/tmp/_TestChown_" + fd, err := Open(Path, O_WRONLY|O_CREAT, 0666) if err != nil { t.Fatalf("create %s: %s", Path, err) } - dir, err := fd.Stat(); + dir, err := fd.Stat() if err != nil { t.Fatalf("fstat %s: %s", Path, err) } - defer fd.Close(); - defer Remove(Path); + defer fd.Close() + defer Remove(Path) // Can't change uid unless root, but can try // changing the group id. First try our current group. - gid := Getgid(); - t.Log("gid:", gid); + gid := Getgid() + t.Log("gid:", gid) if err = Chown(Path, -1, gid); err != nil { t.Fatalf("chown %s -1 %d: %s", Path, gid, err) } - checkUidGid(t, Path, int(dir.Uid), gid); + checkUidGid(t, Path, int(dir.Uid), gid) // Then try all the auxiliary groups. - groups, err := Getgroups(); + groups, err := Getgroups() if err != nil { t.Fatalf("getgroups: %s", err) } - t.Log("groups: ", groups); + t.Log("groups: ", groups) for _, g := range groups { if err = Chown(Path, -1, g); err != nil { t.Fatalf("chown %s -1 %d: %s", Path, g, err) } - checkUidGid(t, Path, int(dir.Uid), g); + checkUidGid(t, Path, int(dir.Uid), g) // change back to gid to test fd.Chown if err = fd.Chown(-1, gid); err != nil { t.Fatalf("fchown %s -1 %d: %s", Path, gid, err) } - checkUidGid(t, Path, int(dir.Uid), gid); + checkUidGid(t, Path, int(dir.Uid), gid) } } func checkSize(t *testing.T, path string, size uint64) { - dir, err := Stat(path); + dir, err := Stat(path) if err != nil { t.Fatalf("Stat %q (looking for size %d): %s", path, size, err) } @@ -460,73 +460,73 @@ func checkSize(t *testing.T, path string, size uint64) { } func TestTruncate(t *testing.T) { - MkdirAll("_obj", 0777); - const Path = "_obj/_TestTruncate_"; - fd, err := Open(Path, O_WRONLY|O_CREAT, 0666); + MkdirAll("_obj", 0777) + const Path = "_obj/_TestTruncate_" + fd, err := Open(Path, O_WRONLY|O_CREAT, 0666) if err != nil { t.Fatalf("create %s: %s", Path, err) } - checkSize(t, Path, 0); - fd.Write(strings.Bytes("hello, world\n")); - checkSize(t, Path, 13); - fd.Truncate(10); - checkSize(t, Path, 10); - fd.Truncate(1024); - checkSize(t, Path, 1024); - fd.Truncate(0); - checkSize(t, Path, 0); - fd.Write(strings.Bytes("surprise!")); - checkSize(t, Path, 13+9); // wrote at offset past where hello, world was. - fd.Close(); - Remove(Path); + checkSize(t, Path, 0) + fd.Write(strings.Bytes("hello, world\n")) + checkSize(t, Path, 13) + fd.Truncate(10) + checkSize(t, Path, 10) + fd.Truncate(1024) + checkSize(t, Path, 1024) + fd.Truncate(0) + checkSize(t, Path, 0) + fd.Write(strings.Bytes("surprise!")) + checkSize(t, Path, 13+9) // wrote at offset past where hello, world was. + fd.Close() + Remove(Path) } func TestChdirAndGetwd(t *testing.T) { - fd, err := Open(".", O_RDONLY, 0); + fd, err := Open(".", O_RDONLY, 0) if err != nil { t.Fatalf("Open .: %s", err) } // These are chosen carefully not to be symlinks on a Mac // (unlike, say, /var, /etc, and /tmp). - dirs := []string{"/bin", "/", "/usr/bin"}; + dirs := []string{"/bin", "/", "/usr/bin"} for mode := 0; mode < 2; mode++ { for _, d := range dirs { if mode == 0 { err = Chdir(d) } else { - fd1, err := Open(d, O_RDONLY, 0); + fd1, err := Open(d, O_RDONLY, 0) if err != nil { - t.Errorf("Open %s: %s", d, err); - continue; + t.Errorf("Open %s: %s", d, err) + continue } - err = fd1.Chdir(); - fd1.Close(); + err = fd1.Chdir() + fd1.Close() } - pwd, err1 := Getwd(); - err2 := fd.Chdir(); + pwd, err1 := Getwd() + err2 := fd.Chdir() if err2 != nil { // We changed the current directory and cannot go back. // Don't let the tests continue; they'll scribble // all over some other directory. - fmt.Fprintf(Stderr, "fchdir back to dot failed: %s\n", err2); - Exit(1); + fmt.Fprintf(Stderr, "fchdir back to dot failed: %s\n", err2) + Exit(1) } if err != nil { - fd.Close(); - t.Fatalf("Chdir %s: %s", d, err); + fd.Close() + t.Fatalf("Chdir %s: %s", d, err) } if err1 != nil { - fd.Close(); - t.Fatalf("Getwd in %s: %s", d, err1); + fd.Close() + t.Fatalf("Getwd in %s: %s", d, err1) } if pwd != d { - fd.Close(); - t.Fatalf("Getwd returned %q want %q", pwd, d); + fd.Close() + t.Fatalf("Getwd returned %q want %q", pwd, d) } } } - fd.Close(); + fd.Close() } func TestTime(t *testing.T) { @@ -536,25 +536,25 @@ func TestTime(t *testing.T) { // filling in the structure passed to the system call. // Too bad the compiler doesn't know that // 365.24*86400 is an integer. - sec, nsec, err := Time(); + sec, nsec, err := Time() if sec < (2009-1970)*36524*864 { t.Errorf("Time() = %d, %d, %s; not plausible", sec, nsec, err) } } func TestSeek(t *testing.T) { - f, err := Open("_obj/seektest", O_CREAT|O_RDWR|O_TRUNC, 0666); + f, err := Open("_obj/seektest", O_CREAT|O_RDWR|O_TRUNC, 0666) if err != nil { t.Fatalf("open _obj/seektest: %s", err) } - const data = "hello, world\n"; - io.WriteString(f, data); + const data = "hello, world\n" + io.WriteString(f, data) type test struct { - in int64; - whence int; - out int64; + in int64 + whence int + out int64 } var tests = []test{ test{0, 1, int64(len(data))}, @@ -565,25 +565,25 @@ func TestSeek(t *testing.T) { test{-1, 2, int64(len(data)) - 1}, test{1 << 33, 0, 1 << 33}, test{1 << 33, 2, 1<<33 + int64(len(data))}, - }; + } for i, tt := range tests { - off, err := f.Seek(tt.in, tt.whence); + off, err := f.Seek(tt.in, tt.whence) if off != tt.out || err != nil { if e, ok := err.(*PathError); ok && e.Error == EINVAL && tt.out > 1<<32 { // Reiserfs rejects the big seeks. // http://code.google.com/p/go/issues/detail?id=91 break } - t.Errorf("#%d: Seek(%v, %v) = %v, %v want %v, nil", i, tt.in, tt.whence, off, err, tt.out); + t.Errorf("#%d: Seek(%v, %v) = %v, %v want %v, nil", i, tt.in, tt.whence, off, err, tt.out) } } - f.Close(); + f.Close() } type openErrorTest struct { - path string; - mode int; - error string; + path string + mode int + error string } var openErrorTests = []openErrorTest{ @@ -606,11 +606,11 @@ var openErrorTests = []openErrorTest{ func TestOpenError(t *testing.T) { for _, tt := range openErrorTests { - f, err := Open(tt.path, tt.mode, 0); + f, err := Open(tt.path, tt.mode, 0) if err == nil { - t.Errorf("Open(%q, %d) succeeded", tt.path, tt.mode); - f.Close(); - continue; + t.Errorf("Open(%q, %d) succeeded", tt.path, tt.mode) + f.Close() + continue } if s := err.String(); s != tt.error { t.Errorf("Open(%q, %d) = _, %q; want %q", tt.path, tt.mode, s, tt.error) @@ -620,20 +620,20 @@ func TestOpenError(t *testing.T) { func run(t *testing.T, cmd []string) string { // Run /bin/hostname and collect output. - r, w, err := Pipe(); + r, w, err := Pipe() if err != nil { t.Fatal(err) } - pid, err := ForkExec("/bin/hostname", []string{"hostname"}, nil, "/", []*File{nil, w, Stderr}); + pid, err := ForkExec("/bin/hostname", []string{"hostname"}, nil, "/", []*File{nil, w, Stderr}) if err != nil { t.Fatal(err) } - w.Close(); + w.Close() - var b bytes.Buffer; - io.Copy(&b, r); - Wait(pid, 0); - output := b.String(); + var b bytes.Buffer + io.Copy(&b, r) + Wait(pid, 0) + output := b.String() if n := len(output); n > 0 && output[n-1] == '\n' { output = output[0 : n-1] } @@ -641,32 +641,32 @@ func run(t *testing.T, cmd []string) string { t.Fatalf("%v produced no output", cmd) } - return output; + return output } func TestHostname(t *testing.T) { // Check internal Hostname() against the output of /bin/hostname. - hostname, err := Hostname(); + hostname, err := Hostname() if err != nil { t.Fatalf("%v", err) } - want := run(t, []string{"/bin/hostname"}); + want := run(t, []string{"/bin/hostname"}) if hostname != want { t.Errorf("Hostname() = %q, want %q", hostname, want) } } func TestReadAt(t *testing.T) { - f, err := Open("_obj/readtest", O_CREAT|O_RDWR|O_TRUNC, 0666); + f, err := Open("_obj/readtest", O_CREAT|O_RDWR|O_TRUNC, 0666) if err != nil { t.Fatalf("open _obj/readtest: %s", err) } - const data = "hello, world\n"; - io.WriteString(f, data); + const data = "hello, world\n" + io.WriteString(f, data) - b := make([]byte, 5); - n, err := f.ReadAt(b, 7); + b := make([]byte, 5) + n, err := f.ReadAt(b, 7) if err != nil || n != len(b) { t.Fatalf("ReadAt 7: %d, %r", n, err) } @@ -676,19 +676,19 @@ func TestReadAt(t *testing.T) { } func TestWriteAt(t *testing.T) { - f, err := Open("_obj/writetest", O_CREAT|O_RDWR|O_TRUNC, 0666); + f, err := Open("_obj/writetest", O_CREAT|O_RDWR|O_TRUNC, 0666) if err != nil { t.Fatalf("open _obj/writetest: %s", err) } - const data = "hello, world\n"; - io.WriteString(f, data); + const data = "hello, world\n" + io.WriteString(f, data) - n, err := f.WriteAt(strings.Bytes("WORLD"), 7); + n, err := f.WriteAt(strings.Bytes("WORLD"), 7) if err != nil || n != 5 { t.Fatalf("WriteAt 7: %d, %v", n, err) } - b, err := ioutil.ReadFile("_obj/writetest"); + b, err := ioutil.ReadFile("_obj/writetest") if err != nil { t.Fatalf("ReadFile _obj/writetest: %v", err) } |