github.com/jaypipes/ghw@v0.21.1/pkg/cpu/cpu_linux_test.go (about)

     1  //
     2  // Use and distribution licensed under the Apache license version 2.
     3  //
     4  // See the COPYING file in the root project directory for full text.
     5  //
     6  
     7  package cpu_test
     8  
     9  import (
    10  	"bytes"
    11  	"io"
    12  	"os"
    13  	"path/filepath"
    14  	"strings"
    15  	"testing"
    16  
    17  	"github.com/jaypipes/ghw/pkg/cpu"
    18  	"github.com/jaypipes/ghw/pkg/option"
    19  	"github.com/jaypipes/ghw/pkg/topology"
    20  	"github.com/jaypipes/ghw/testdata"
    21  )
    22  
    23  // nolint: gocyclo
    24  func TestArmCPU(t *testing.T) {
    25  	if _, ok := os.LookupEnv("GHW_TESTING_SKIP_CPU"); ok {
    26  		t.Skip("Skipping CPU tests.")
    27  	}
    28  
    29  	testdataPath, err := testdata.SnapshotsDirectory()
    30  	if err != nil {
    31  		t.Fatalf("Expected nil err, but got %v", err)
    32  	}
    33  
    34  	multiNumaSnapshot := filepath.Join(testdataPath, "linux-arm64-c288e0776090cd558ef793b2a4e61939.tar.gz")
    35  
    36  	info, err := cpu.New(option.WithSnapshot(option.SnapshotOptions{
    37  		Path: multiNumaSnapshot,
    38  	}))
    39  
    40  	if err != nil {
    41  		t.Fatalf("Expected nil err, but got %v", err)
    42  	}
    43  	if info == nil {
    44  		t.Fatalf("Expected non-nil CPUInfo, but got nil")
    45  	}
    46  
    47  	if len(info.Processors) == 0 {
    48  		t.Fatalf("Expected >0 processors but got 0.")
    49  	}
    50  
    51  	for _, p := range info.Processors {
    52  		if p.Vendor == "" {
    53  			t.Fatalf("Expected not empty vendor field.")
    54  		}
    55  		if p.TotalCores == 0 {
    56  			t.Fatalf("Expected >0 cores but got 0.")
    57  		}
    58  		if p.TotalHardwareThreads == 0 {
    59  			t.Fatalf("Expected >0 threads but got 0.")
    60  		}
    61  		if len(p.Capabilities) == 0 {
    62  			t.Fatalf("Expected >0 capabilities but got 0.")
    63  		}
    64  		if !p.HasCapability(p.Capabilities[0]) {
    65  			t.Fatalf("Expected p to have capability %s, but did not.",
    66  				p.Capabilities[0])
    67  		}
    68  		if len(p.Cores) == 0 {
    69  			t.Fatalf("Expected >0 cores in processor, but got 0.")
    70  		}
    71  		for _, c := range p.Cores {
    72  			if c.TotalHardwareThreads == 0 {
    73  				t.Fatalf("Expected >0 threads but got 0.")
    74  			}
    75  			if len(c.LogicalProcessors) == 0 {
    76  				t.Fatalf("Expected >0 logical processors but got 0.")
    77  			}
    78  		}
    79  	}
    80  }
    81  
    82  func TestCheckCPUTopologyFilesForOfflineCPU(t *testing.T) {
    83  	if _, ok := os.LookupEnv("GHW_TESTING_SKIP_CPU"); ok {
    84  		t.Skip("Skipping CPU tests.")
    85  	}
    86  
    87  	testdataPath, err := testdata.SnapshotsDirectory()
    88  	if err != nil {
    89  		t.Fatalf("Expected nil err, but got %v", err)
    90  	}
    91  
    92  	offlineCPUSnapshot := filepath.Join(testdataPath, "linux-amd64-offlineCPUs.tar.gz")
    93  
    94  	// Capture stderr
    95  	rErr, wErr, err := os.Pipe()
    96  	if err != nil {
    97  		t.Fatalf("Cannot pipe StdErr. %v", err)
    98  	}
    99  	os.Stderr = wErr
   100  
   101  	info, err := cpu.New(option.WithSnapshot(option.SnapshotOptions{
   102  		Path: offlineCPUSnapshot,
   103  	}))
   104  	if err != nil {
   105  		t.Fatalf("Expected nil err, but got %v", err)
   106  	}
   107  	if info == nil {
   108  		t.Fatalf("Expected non-nil CPUInfo, but got nil")
   109  	}
   110  
   111  	if len(info.Processors) == 0 {
   112  		t.Fatalf("Expected >0 processors but got 0.")
   113  	}
   114  	wErr.Close()
   115  	var bufErr bytes.Buffer
   116  	if _, err := io.Copy(&bufErr, rErr); err != nil {
   117  		t.Fatalf("Failed to copy data to buffer: %v", err)
   118  	}
   119  	errorOutput := bufErr.String()
   120  	if strings.Contains(errorOutput, "WARNING: failed to read int from file:") {
   121  		t.Fatalf("Unexpected warning related to missing files under topology directory was reported")
   122  	}
   123  }
   124  
   125  func TestNumCoresAmongOfflineCPUs(t *testing.T) {
   126  	if _, ok := os.LookupEnv("GHW_TESTING_SKIP_CPU"); ok {
   127  		t.Skip("Skipping CPU tests.")
   128  	}
   129  
   130  	testdataPath, err := testdata.SnapshotsDirectory()
   131  	if err != nil {
   132  		t.Fatalf("Expected nil err, but got %v", err)
   133  	}
   134  
   135  	offlineCPUSnapshot := filepath.Join(testdataPath, "linux-amd64-offlineCPUs.tar.gz")
   136  
   137  	// Capture stderr
   138  	rErr, wErr, err := os.Pipe()
   139  	if err != nil {
   140  		t.Fatalf("Cannot pipe the StdErr. %v", err)
   141  	}
   142  	info, err := topology.New(option.WithSnapshot(option.SnapshotOptions{
   143  		Path: offlineCPUSnapshot,
   144  	}))
   145  	if err != nil {
   146  		t.Fatalf("Error determining node topology. %v", err)
   147  	}
   148  
   149  	if len(info.Nodes) < 1 {
   150  		t.Fatal("No nodes found. Must contain one or more nodes")
   151  	}
   152  	for _, node := range info.Nodes {
   153  		if len(node.Cores) < 1 {
   154  			t.Fatal("No cores found. Must contain one or more cores")
   155  		}
   156  	}
   157  	wErr.Close()
   158  	var bufErr bytes.Buffer
   159  	if _, err := io.Copy(&bufErr, rErr); err != nil {
   160  		t.Fatalf("Failed to copy data to buffer: %v", err)
   161  	}
   162  	errorOutput := bufErr.String()
   163  	if strings.Contains(errorOutput, "WARNING: failed to read int from file:") {
   164  		t.Fatalf("Unexpected warnings related to missing files under topology directory was raised")
   165  	}
   166  }