github.com/shaardie/u-root@v4.0.1-0.20190127173353-f24a1c26aa2e+incompatible/pkg/kexec/memory_linux_test.go (about) 1 // Copyright 2018-2019 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 kexec 6 7 import ( 8 "bytes" 9 "fmt" 10 "io/ioutil" 11 "os" 12 "path" 13 "reflect" 14 "testing" 15 ) 16 17 func TestParseMemoryMap(t *testing.T) { 18 var mem Memory 19 root, err := ioutil.TempDir("", "memmap") 20 if err != nil { 21 t.Fatalf("Cannot create test dir: %v", err) 22 } 23 defer os.RemoveAll(root) 24 25 old := memoryMapRoot 26 memoryMapRoot = root 27 defer func() { memoryMapRoot = old }() 28 29 create := func(dir string, start, end uintptr, typ RangeType) error { 30 p := path.Join(root, dir) 31 if err := os.Mkdir(p, 0755); err != nil { 32 return err 33 } 34 if err := ioutil.WriteFile(path.Join(p, "start"), []byte(fmt.Sprintf("%#x\n", start)), 0655); err != nil { 35 return err 36 } 37 if err := ioutil.WriteFile(path.Join(p, "end"), []byte(fmt.Sprintf("%#x\n", end)), 0655); err != nil { 38 return err 39 } 40 return ioutil.WriteFile(path.Join(p, "type"), append([]byte(typ), '\n'), 0655) 41 } 42 43 if err := create("0", 0, 50, RangeRAM); err != nil { 44 t.Fatal(err) 45 } 46 if err := create("1", 100, 150, RangeNVACPI); err != nil { 47 t.Fatal(err) 48 } 49 if err := create("2", 200, 250, RangeACPI); err != nil { 50 t.Fatal(err) 51 } 52 if err := create("3", 300, 350, RangeNVS); err != nil { 53 t.Fatal(err) 54 } 55 56 want := []TypedAddressRange{ 57 {Range: Range{Start: 0, Size: 50}, Type: RangeRAM}, 58 {Range: Range{Start: 100, Size: 50}, Type: RangeNVACPI}, 59 {Range: Range{Start: 200, Size: 50}, Type: RangeACPI}, 60 {Range: Range{Start: 300, Size: 50}, Type: RangeNVS}, 61 } 62 63 if err := mem.ParseMemoryMap(); err != nil { 64 t.Fatalf("ParseMemoryMap() error: %v", err) 65 } 66 if !reflect.DeepEqual(mem.Phys, want) { 67 t.Errorf("ParseMemoryMap() got %v, want %v", mem.Phys, want) 68 } 69 } 70 71 func TestAvailableRAM(t *testing.T) { 72 old := pageMask 73 defer func() { 74 pageMask = old 75 }() 76 // suppose we have 4K pages. 77 pageMask = 4095 78 79 var mem Memory 80 mem.Phys = []TypedAddressRange{ 81 TypedAddressRange{Range: Range{Start: 0, Size: 8192}, Type: RangeRAM}, 82 TypedAddressRange{Range: Range{Start: 8192, Size: 8000}, Type: RangeRAM}, 83 TypedAddressRange{Range: Range{Start: 20480, Size: 1000}, Type: RangeRAM}, 84 TypedAddressRange{Range: Range{Start: 24576, Size: 1000}, Type: RangeRAM}, 85 TypedAddressRange{Range: Range{Start: 28672, Size: 1000}, Type: RangeRAM}, 86 } 87 88 mem.Segments = []Segment{ 89 Segment{Phys: Range{Start: 40, Size: 50}}, 90 Segment{Phys: Range{Start: 8000, Size: 200}}, 91 Segment{Phys: Range{Start: 18000, Size: 1000}}, 92 Segment{Phys: Range{Start: 24600, Size: 1000}}, 93 Segment{Phys: Range{Start: 28000, Size: 10000}}, 94 } 95 96 want := []TypedAddressRange{ 97 TypedAddressRange{Range: Range{Start: 0, Size: 40}, Type: RangeRAM}, 98 TypedAddressRange{Range: Range{Start: 4096, Size: 8000 - 4096}, Type: RangeRAM}, 99 TypedAddressRange{Range: Range{Start: 12288, Size: 8192 + 8000 - 12288}, Type: RangeRAM}, 100 TypedAddressRange{Range: Range{Start: 20480, Size: 1000}, Type: RangeRAM}, 101 TypedAddressRange{Range: Range{Start: 24576, Size: 24}, Type: RangeRAM}, 102 } 103 104 got := mem.availableRAM() 105 if !reflect.DeepEqual(got, want) { 106 t.Errorf("availableRAM() got %+v, want %+v", got, want) 107 } 108 } 109 110 func TestAlignPhys(t *testing.T) { 111 for _, test := range []struct { 112 name string 113 seg, want Segment 114 }{ 115 { 116 name: "aligned", 117 seg: Segment{ 118 Buf: Range{Start: 0x1000, Size: 0x1000}, 119 Phys: Range{Start: 0x2000, Size: 0x1000}, 120 }, 121 want: Segment{ 122 Buf: Range{Start: 0x1000, Size: 0x1000}, 123 Phys: Range{Start: 0x2000, Size: 0x1000}, 124 }, 125 }, 126 { 127 name: "unaligned", 128 seg: Segment{ 129 Buf: Range{Start: 0x1011, Size: 0x1022}, 130 Phys: Range{Start: 0x2011, Size: 0x1022}, 131 }, 132 want: Segment{ 133 Buf: Range{Start: 0x1000, Size: 0x1033}, 134 Phys: Range{Start: 0x2000, Size: 0x2000}, 135 }, 136 }, 137 { 138 name: "empty_buf", 139 seg: Segment{ 140 Buf: Range{Start: 0x1011, Size: 0}, 141 Phys: Range{Start: 0x2011, Size: 0}, 142 }, 143 want: Segment{ 144 Buf: Range{Start: 0x1000, Size: 0}, 145 Phys: Range{Start: 0x2000, Size: 0x1000}, 146 }, 147 }, 148 } { 149 t.Run(test.name, func(t *testing.T) { 150 got := AlignPhys(test.seg) 151 if got != test.want { 152 t.Errorf("AlignPhys() got %v, want %v", got, test.want) 153 } 154 }) 155 } 156 } 157 158 func TestTryMerge(t *testing.T) { 159 for _, test := range []struct { 160 name string 161 phys Range 162 merged bool 163 want Range 164 }{ 165 { 166 name: "disjunct", 167 phys: Range{Start: 100, Size: 150}, 168 merged: false, 169 }, 170 { 171 name: "superset", 172 phys: Range{Start: 0, Size: 80}, 173 merged: true, 174 want: Range{Start: 0, Size: 100}, 175 }, 176 { 177 name: "superset", 178 phys: Range{Start: 10, Size: 80}, 179 merged: true, 180 want: Range{Start: 0, Size: 100}, 181 }, 182 { 183 name: "superset", 184 phys: Range{Start: 10, Size: 90}, 185 merged: true, 186 want: Range{Start: 0, Size: 100}, 187 }, 188 { 189 name: "superset", 190 phys: Range{Start: 0, Size: 100}, 191 merged: true, 192 want: Range{Start: 0, Size: 100}, 193 }, 194 { 195 name: "overlap", 196 phys: Range{Start: 0, Size: 150}, 197 merged: true, 198 want: Range{Start: 0, Size: 150}, 199 }, 200 { 201 name: "overlap", 202 phys: Range{Start: 50, Size: 100}, 203 merged: true, 204 want: Range{Start: 0, Size: 150}, 205 }, 206 { 207 name: "overlap", 208 phys: Range{Start: 99, Size: 51}, 209 merged: true, 210 want: Range{Start: 0, Size: 150}, 211 }, 212 } { 213 t.Run(test.name, func(t *testing.T) { 214 a := NewSegment([]byte("aaaa"), Range{Start: 0, Size: 100}) 215 b := NewSegment([]byte("bbbb"), test.phys) 216 217 merged := a.tryMerge(b) 218 if merged != test.merged { 219 t.Fatalf("tryMerge() got %v, want %v", merged, test.merged) 220 } 221 if !merged { 222 return 223 } 224 if a.Phys != test.want { 225 t.Fatalf("Wrong merge result: got %+v, want %+v", a.Phys, test.want) 226 } 227 228 got := a.Buf.toSlice() 229 want := []byte("aaaabbbb") 230 if !bytes.Equal(got, want) { 231 t.Errorf("Wrong buf: got %s, want %s", got, want) 232 } 233 }) 234 } 235 } 236 237 func TestDedup(t *testing.T) { 238 s := []Segment{ 239 NewSegment([]byte("test"), Range{Start: 0, Size: 100}), 240 NewSegment([]byte("test"), Range{Start: 100, Size: 100}), 241 NewSegment([]byte("test"), Range{Start: 200, Size: 100}), 242 NewSegment([]byte("test"), Range{Start: 250, Size: 50}), 243 NewSegment([]byte("test"), Range{Start: 300, Size: 100}), 244 NewSegment([]byte("test"), Range{Start: 350, Size: 100}), 245 } 246 want := []Range{ 247 Range{Start: 0, Size: 100}, 248 Range{Start: 100, Size: 100}, 249 Range{Start: 200, Size: 100}, 250 Range{Start: 300, Size: 150}, 251 } 252 253 got := Dedup(s) 254 for i := range got { 255 if got[i].Phys != want[i] { 256 t.Errorf("Dedup() got %v, want %v", got[i].Phys, want[i]) 257 } 258 } 259 260 }