package mount import ( "os" "path/filepath" "testing" ) func TestSetupAndTeardownWithFakeCommands(t *testing.T) { dir := t.TempDir() scripts := filepath.Join(dir, "bin") if err := os.MkdirAll(scripts, 0o755); err != nil { t.Fatal(err) } write := func(name, body string) { path := filepath.Join(scripts, name) if err := os.WriteFile(path, []byte("#!/usr/bin/env bash\nset -eu\n"+body+"\n"), 0o755); err != nil { t.Fatalf("write %s: %v", name, err) } } write("losetup", `printf '/dev/loop9\n'`) write("mount", `exit 0`) write("umount", `exit 0`) t.Setenv("PATH", scripts+string(os.PathListSeparator)+os.Getenv("PATH")) image := filepath.Join(dir, "image.img") if err := os.WriteFile(image, make([]byte, 1024), 0o644); err != nil { t.Fatal(err) } if err := os.WriteFile(image+"p1", []byte(""), 0o644); err != nil { t.Fatal(err) } if got := partitionPath(image, 1); got != image+"p1" { t.Fatalf("partitionPath existing = %q", got) } m, err := Setup(image) if err != nil { t.Fatalf("Setup: %v", err) } if m.LoopDevice != "/dev/loop9" || m.BootPath == "" || m.RootPath == "" { t.Fatalf("unexpected mount: %#v", m) } if err := Teardown(m); err != nil { t.Fatalf("Teardown: %v", err) } if got := partitionPath("/dev/loop9", 2); got != "/dev/loop92" && got != "/dev/loop9p2" { t.Fatalf("partitionPath /dev = %q", got) } } func TestSetupReportsLoopAndTempDirFailures(t *testing.T) { dir := t.TempDir() scripts := filepath.Join(dir, "bin") if err := os.MkdirAll(scripts, 0o755); err != nil { t.Fatal(err) } write := func(name, body string) { path := filepath.Join(scripts, name) if err := os.WriteFile(path, []byte("#!/usr/bin/env bash\nset -eu\n"+body+"\n"), 0o755); err != nil { t.Fatalf("write %s: %v", name, err) } } write("losetup", `exit 2`) write("mount", `exit 0`) write("umount", `exit 0`) t.Setenv("PATH", scripts+string(os.PathListSeparator)+os.Getenv("PATH")) if _, err := Setup(filepath.Join(dir, "image.img")); err == nil { t.Fatal("expected losetup failure") } tmpFile := filepath.Join(dir, "tmp-file") if err := os.WriteFile(tmpFile, []byte("not-a-dir"), 0o644); err != nil { t.Fatal(err) } t.Setenv("TMPDIR", tmpFile) if _, err := Setup("/dev/loop9"); err == nil { t.Fatal("expected temp-dir creation failure") } } func TestSetupReportsMountFailures(t *testing.T) { t.Run("boot", func(t *testing.T) { dir := t.TempDir() scripts := filepath.Join(dir, "bin") if err := os.MkdirAll(scripts, 0o755); err != nil { t.Fatal(err) } write := func(name, body string) { path := filepath.Join(scripts, name) if err := os.WriteFile(path, []byte("#!/usr/bin/env bash\nset -eu\n"+body+"\n"), 0o755); err != nil { t.Fatalf("write %s: %v", name, err) } } write("mount", `exit 3`) write("umount", `exit 0`) write("losetup", `exit 0`) t.Setenv("PATH", scripts+string(os.PathListSeparator)+os.Getenv("PATH")) if _, err := Setup("/dev/loop9"); err == nil { t.Fatal("expected boot mount failure") } }) t.Run("root", func(t *testing.T) { dir := t.TempDir() scripts := filepath.Join(dir, "bin") if err := os.MkdirAll(scripts, 0o755); err != nil { t.Fatal(err) } state := filepath.Join(dir, "mount-count") write := func(name, body string) { path := filepath.Join(scripts, name) if err := os.WriteFile(path, []byte("#!/usr/bin/env bash\nset -eu\n"+body+"\n"), 0o755); err != nil { t.Fatalf("write %s: %v", name, err) } } write("mount", `state="`+state+`" count=0 if [[ -f "$state" ]]; then count="$(cat "$state")"; fi count=$((count + 1)) printf '%s' "$count" > "$state" if [[ "$count" == "2" ]]; then exit 4; fi exit 0`) write("umount", `exit 0`) write("losetup", `exit 0`) t.Setenv("PATH", scripts+string(os.PathListSeparator)+os.Getenv("PATH")) if _, err := Setup("/dev/loop9"); err == nil { t.Fatal("expected root mount failure") } }) }