github.com/mvdan/u-root-coreutils@v0.0.0-20230122170626-c2eef2898555/pkg/uroot/uroot_test.go (about) 1 // Copyright 2018 the u-root Authors. All rights reserved 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 package uroot 6 7 import ( 8 "fmt" 9 "os" 10 "path/filepath" 11 "syscall" 12 "testing" 13 14 "github.com/mvdan/u-root-coreutils/pkg/cpio" 15 "github.com/mvdan/u-root-coreutils/pkg/ulog/ulogtest" 16 "github.com/mvdan/u-root-coreutils/pkg/uroot/builder" 17 itest "github.com/mvdan/u-root-coreutils/pkg/uroot/initramfs/test" 18 ) 19 20 type inMemArchive struct { 21 *cpio.Archive 22 } 23 24 // Finish implements initramfs.Writer.Finish. 25 func (inMemArchive) Finish() error { return nil } 26 27 func TestCreateInitramfs(t *testing.T) { 28 dir := t.TempDir() 29 syscall.Umask(0) 30 31 urootpath, err := filepath.Abs("../../") 32 if err != nil { 33 t.Fatalf("failure to set up test: %v", err) 34 } 35 36 tmp777 := filepath.Join(dir, "tmp777") 37 if err := os.MkdirAll(tmp777, 0o777); err != nil { 38 t.Error(err) 39 } 40 41 l := ulogtest.Logger{TB: t} 42 43 for i, tt := range []struct { 44 name string 45 opts Opts 46 want string 47 validators []itest.ArchiveValidator 48 }{ 49 { 50 name: "BB archive with ls and init", 51 opts: Opts{ 52 TempDir: dir, 53 ExtraFiles: nil, 54 UseExistingInit: false, 55 InitCmd: "init", 56 DefaultShell: "ls", 57 UrootSource: urootpath, 58 Commands: []Commands{ 59 { 60 Builder: builder.BusyBox, 61 Packages: []string{ 62 "github.com/mvdan/u-root-coreutils/cmds/core/init", 63 "github.com/mvdan/u-root-coreutils/cmds/core/ls", 64 }, 65 }, 66 }, 67 }, 68 want: "", 69 validators: []itest.ArchiveValidator{ 70 itest.HasFile{"bbin/bb"}, 71 itest.HasRecord{cpio.Symlink("bbin/init", "bb")}, 72 itest.HasRecord{cpio.Symlink("bbin/ls", "bb")}, 73 itest.HasRecord{cpio.Symlink("bin/defaultsh", "../bbin/ls")}, 74 itest.HasRecord{cpio.Symlink("bin/sh", "../bbin/ls")}, 75 }, 76 }, 77 { 78 name: "no temp dir", 79 opts: Opts{ 80 InitCmd: "init", 81 DefaultShell: "", 82 }, 83 want: "temp dir \"\" must exist: stat : no such file or directory", 84 validators: []itest.ArchiveValidator{ 85 itest.IsEmpty{}, 86 }, 87 }, 88 { 89 name: "no commands", 90 opts: Opts{ 91 TempDir: dir, 92 }, 93 want: "", 94 validators: []itest.ArchiveValidator{ 95 itest.MissingFile{"bbin/bb"}, 96 }, 97 }, 98 { 99 name: "init specified, but not in commands", 100 opts: Opts{ 101 TempDir: dir, 102 DefaultShell: "zoocar", 103 InitCmd: "foobar", 104 UrootSource: urootpath, 105 Commands: []Commands{ 106 { 107 Builder: builder.Binary, 108 Packages: []string{ 109 "github.com/mvdan/u-root-coreutils/cmds/core/ls", 110 }, 111 }, 112 }, 113 }, 114 want: "could not create symlink from \"init\" to \"foobar\": command or path \"foobar\" not included in u-root build: specify -initcmd=\"\" to ignore this error and build without an init (or, did you specify a list, and are you missing github.com/mvdan/u-root-coreutils/cmds/core/init?)", 115 validators: []itest.ArchiveValidator{ 116 itest.IsEmpty{}, 117 }, 118 }, 119 { 120 name: "init symlinked to absolute path", 121 opts: Opts{ 122 TempDir: dir, 123 InitCmd: "/bin/systemd", 124 }, 125 want: "", 126 validators: []itest.ArchiveValidator{ 127 itest.HasRecord{cpio.Symlink("init", "bin/systemd")}, 128 }, 129 }, 130 { 131 name: "multi-mode archive", 132 opts: Opts{ 133 TempDir: dir, 134 ExtraFiles: nil, 135 UseExistingInit: false, 136 InitCmd: "init", 137 DefaultShell: "ls", 138 UrootSource: urootpath, 139 Commands: []Commands{ 140 { 141 Builder: builder.BusyBox, 142 Packages: []string{ 143 "github.com/mvdan/u-root-coreutils/cmds/core/init", 144 "github.com/mvdan/u-root-coreutils/cmds/core/ls", 145 }, 146 }, 147 { 148 Builder: builder.Binary, 149 Packages: []string{ 150 "github.com/mvdan/u-root-coreutils/cmds/core/cp", 151 "github.com/mvdan/u-root-coreutils/cmds/core/dd", 152 }, 153 }, 154 }, 155 }, 156 want: "", 157 validators: []itest.ArchiveValidator{ 158 itest.HasRecord{cpio.Symlink("init", "bbin/init")}, 159 160 // bb mode. 161 itest.HasFile{"bbin/bb"}, 162 itest.HasRecord{cpio.Symlink("bbin/init", "bb")}, 163 itest.HasRecord{cpio.Symlink("bbin/ls", "bb")}, 164 itest.HasRecord{cpio.Symlink("bin/defaultsh", "../bbin/ls")}, 165 itest.HasRecord{cpio.Symlink("bin/sh", "../bbin/ls")}, 166 167 // binary mode. 168 itest.HasFile{"bin/cp"}, 169 itest.HasFile{"bin/dd"}, 170 }, 171 }, 172 } { 173 t.Run(fmt.Sprintf("Test %d [%s]", i, tt.name), func(t *testing.T) { 174 archive := inMemArchive{cpio.InMemArchive()} 175 tt.opts.OutputFile = archive 176 // Compare error type or error string. 177 if err := CreateInitramfs(l, tt.opts); (err != nil && err.Error() != tt.want) || (len(tt.want) > 0 && err == nil) { 178 t.Errorf("CreateInitramfs(%v) = %v, want %v", tt.opts, err, tt.want) 179 } 180 181 for _, v := range tt.validators { 182 if err := v.Validate(archive.Archive); err != nil { 183 t.Errorf("validator failed: %v / archive:\n%s", err, archive) 184 } 185 } 186 }) 187 } 188 }