github.com/google/cadvisor@v0.49.1/container/common/helpers_test.go (about) 1 // Copyright 2018 Google Inc. All Rights Reserved. 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package common 16 17 import ( 18 "errors" 19 "fmt" 20 "math" 21 "os" 22 "path/filepath" 23 "reflect" 24 "testing" 25 26 "github.com/stretchr/testify/assert" 27 28 "github.com/google/cadvisor/container" 29 info "github.com/google/cadvisor/info/v1" 30 v2 "github.com/google/cadvisor/info/v2" 31 ) 32 33 func BenchmarkListDirectories(b *testing.B) { 34 for i := 0; i < b.N; i++ { 35 output := make(map[string]struct{}) 36 if err := ListDirectories("/sys/fs/cgroup", "", true, output); err != nil { 37 b.Fatal(err) 38 } 39 } 40 } 41 42 func TestConvertCpuWeightToCpuLimit(t *testing.T) { 43 limit, err := convertCPUWeightToCPULimit(1) 44 if err != nil { 45 t.Fatalf("Error in convertCPUWeightToCPULimit: %s", err) 46 } 47 if limit != 2 { 48 t.Fatalf("convertCPUWeightToCPULimit(1) != 2") 49 } 50 limit, err = convertCPUWeightToCPULimit(10000) 51 if err != nil { 52 t.Fatalf("Error in convertCPUWeightToCPULimit: %s", err) 53 } 54 if limit != 262144 { 55 t.Fatalf("convertCPUWeightToCPULimit(10000) != 262144") 56 } 57 _, err = convertCPUWeightToCPULimit(0) 58 if err == nil { 59 t.Fatalf("convertCPUWeightToCPULimit(0) must raise an error") 60 } 61 _, err = convertCPUWeightToCPULimit(10001) 62 if err == nil { 63 t.Fatalf("convertCPUWeightToCPULimit(10001) must raise an error") 64 } 65 } 66 67 func TestParseUint64String(t *testing.T) { 68 if parseUint64String("1000") != 1000 { 69 t.Fatalf("parseUint64String(\"1000\") != 1000") 70 } 71 if parseUint64String("-1") != 0 { 72 t.Fatalf("parseUint64String(\"-1\") != 0") 73 } 74 if parseUint64String("0") != 0 { 75 t.Fatalf("parseUint64String(\"0\") != 0") 76 } 77 if parseUint64String("not-a-number") != 0 { 78 t.Fatalf("parseUint64String(\"not-a-number\") != 0") 79 } 80 if parseUint64String(" 1000 ") != 0 { 81 t.Fatalf("parseUint64String(\" 1000 \") != 0") 82 } 83 if parseUint64String("18446744073709551615") != 18446744073709551615 { 84 t.Fatalf("parseUint64String(\"18446744073709551615\") != 18446744073709551615") 85 } 86 } 87 88 type mockInfoProvider struct { 89 options v2.RequestOptions 90 } 91 92 func (m *mockInfoProvider) GetRequestedContainersInfo(containerName string, options v2.RequestOptions) (map[string]*info.ContainerInfo, error) { 93 m.options = options 94 return map[string]*info.ContainerInfo{}, nil 95 } 96 97 func (m *mockInfoProvider) GetVersionInfo() (*info.VersionInfo, error) { 98 return nil, errors.New("not supported") 99 } 100 101 func (m *mockInfoProvider) GetMachineInfo() (*info.MachineInfo, error) { 102 return &info.MachineInfo{ 103 NumCores: 7, 104 }, nil 105 } 106 107 func TestGetSpecCgroupV1(t *testing.T) { 108 root, err := os.Getwd() 109 if err != nil { 110 t.Fatalf("getwd: %s", err) 111 } 112 113 cgroupPaths := map[string]string{ 114 "memory": filepath.Join(root, "test_resources/cgroup_v1/test1/memory"), 115 "cpu": filepath.Join(root, "test_resources/cgroup_v1/test1/cpu"), 116 "cpuset": filepath.Join(root, "test_resources/cgroup_v1/test1/cpuset"), 117 "pids": filepath.Join(root, "test_resources/cgroup_v1/test1/pids"), 118 } 119 120 spec, err := getSpecInternal(cgroupPaths, &mockInfoProvider{}, false, false, false) 121 assert.Nil(t, err) 122 123 assert.True(t, spec.HasMemory) 124 assert.EqualValues(t, spec.Memory.Limit, 123456789) 125 assert.EqualValues(t, spec.Memory.SwapLimit, 13579) 126 assert.EqualValues(t, spec.Memory.Reservation, 24680) 127 128 assert.True(t, spec.HasCpu) 129 assert.EqualValues(t, spec.Cpu.Limit, 1025) 130 assert.EqualValues(t, spec.Cpu.Period, 100010) 131 assert.EqualValues(t, spec.Cpu.Quota, 20000) 132 133 assert.EqualValues(t, spec.Cpu.Mask, "0-5") 134 135 assert.True(t, spec.HasProcesses) 136 assert.EqualValues(t, spec.Processes.Limit, 1027) 137 138 assert.False(t, spec.HasHugetlb) 139 assert.False(t, spec.HasDiskIo) 140 } 141 142 func TestGetSpecCgroupV2(t *testing.T) { 143 root, err := os.Getwd() 144 if err != nil { 145 t.Fatalf("getwd: %s", err) 146 } 147 148 cgroupPaths := map[string]string{ 149 "": filepath.Join(root, "test_resources/cgroup_v2/test1"), 150 } 151 152 spec, err := getSpecInternal(cgroupPaths, &mockInfoProvider{}, false, false, true) 153 assert.Nil(t, err) 154 155 assert.True(t, spec.HasMemory) 156 assert.EqualValues(t, spec.Memory.Limit, 123456789) 157 assert.EqualValues(t, spec.Memory.SwapLimit, 13579) 158 assert.EqualValues(t, spec.Memory.Reservation, 24680) 159 160 assert.True(t, spec.HasCpu) 161 assert.EqualValues(t, spec.Cpu.Limit, 1286) 162 assert.EqualValues(t, spec.Cpu.Period, 100010) 163 assert.EqualValues(t, spec.Cpu.Quota, 20000) 164 165 assert.EqualValues(t, spec.Cpu.Mask, "0-5") 166 167 assert.True(t, spec.HasProcesses) 168 assert.EqualValues(t, spec.Processes.Limit, 1027) 169 170 assert.False(t, spec.HasHugetlb) 171 assert.True(t, spec.HasDiskIo) 172 } 173 174 func TestGetSpecCgroupV2Max(t *testing.T) { 175 root, err := os.Getwd() 176 assert.Nil(t, err) 177 178 cgroupPaths := map[string]string{ 179 "": filepath.Join(root, "test_resources/cgroup_v2/test2"), 180 } 181 182 spec, err := getSpecInternal(cgroupPaths, &mockInfoProvider{}, false, false, true) 183 assert.Nil(t, err) 184 185 max := uint64(math.MaxUint64) 186 187 assert.True(t, spec.HasMemory) 188 assert.EqualValues(t, spec.Memory.Limit, max) 189 assert.EqualValues(t, spec.Memory.SwapLimit, max) 190 assert.EqualValues(t, spec.Memory.Reservation, max) 191 192 assert.True(t, spec.HasCpu) 193 assert.EqualValues(t, spec.Cpu.Limit, 1286) 194 assert.EqualValues(t, spec.Cpu.Period, 100010) 195 assert.EqualValues(t, spec.Cpu.Quota, 0) 196 197 assert.EqualValues(t, spec.Processes.Limit, max) 198 } 199 200 func TestRemoveNetMetrics(t *testing.T) { 201 for _, ts := range []struct { 202 desc string 203 in, out container.MetricSet 204 }{ 205 { 206 desc: "nil set", 207 in: nil, 208 }, 209 { 210 desc: "empty set", 211 in: container.MetricSet{}, 212 }, 213 { 214 desc: "nothing to remove", 215 in: container.MetricSet{container.MemoryUsageMetrics: struct{}{}, container.PerfMetrics: struct{}{}}, 216 }, 217 { 218 desc: "also nothing to remove", 219 in: container.AllMetrics.Difference(container.AllNetworkMetrics), 220 }, 221 { 222 desc: "remove net from all", 223 in: container.AllMetrics, 224 out: container.AllMetrics.Difference(container.AllNetworkMetrics), 225 }, 226 { 227 desc: "remove net from some", 228 in: container.MetricSet{container.MemoryUsageMetrics: struct{}{}, container.NetworkTcpUsageMetrics: struct{}{}}, 229 out: container.MetricSet{container.MemoryUsageMetrics: struct{}{}}, 230 }, 231 } { 232 for _, remove := range []bool{true, false} { 233 ts, remove := ts, remove 234 desc := fmt.Sprintf("%s, remove: %v", ts.desc, remove) 235 t.Run(desc, func(t *testing.T) { 236 out := RemoveNetMetrics(ts.in, remove) 237 if !remove || ts.out == nil { 238 // Compare the actual underlying pointers. Can't use assert.Same 239 // because it checks for pointer type, and these are maps. 240 if reflect.ValueOf(ts.in) != reflect.ValueOf(out) { 241 t.Errorf("expected original map %p, got %p", ts.in, out) 242 } 243 } else { 244 assert.Equal(t, ts.out, out) 245 } 246 }) 247 } 248 } 249 } 250 251 func BenchmarkGetSpecCgroupV2(b *testing.B) { 252 root, err := os.Getwd() 253 if err != nil { 254 b.Fatalf("getwd: %s", err) 255 } 256 257 cgroupPaths := map[string]string{ 258 "": filepath.Join(root, "test_resources/cgroup_v2/test1"), 259 } 260 261 for i := 0; i < b.N; i++ { 262 _, err := getSpecInternal(cgroupPaths, &mockInfoProvider{}, false, false, true) 263 assert.Nil(b, err) 264 } 265 266 } 267 268 func BenchmarkGetSpecCgroupV1(b *testing.B) { 269 root, err := os.Getwd() 270 if err != nil { 271 b.Fatalf("getwd: %s", err) 272 } 273 274 cgroupPaths := map[string]string{ 275 "memory": filepath.Join(root, "test_resources/cgroup_v1/test1/memory"), 276 "cpu": filepath.Join(root, "test_resources/cgroup_v1/test1/cpu"), 277 "cpuset": filepath.Join(root, "test_resources/cgroup_v1/test1/cpuset"), 278 "pids": filepath.Join(root, "test_resources/cgroup_v1/test1/pids"), 279 } 280 281 for i := 0; i < b.N; i++ { 282 _, err := getSpecInternal(cgroupPaths, &mockInfoProvider{}, false, false, false) 283 assert.Nil(b, err) 284 } 285 286 }