open-nomad/helper/stats/cpu.go
Charlie Voiselle d64b02f07d Override 3 sec. WMI timeout in gopsutil
The default timeout is too short for some overburdened or resource
constrained machines to complete the WMI query before the context
deadline expires.  This causes them to be unable to fingerprint the CPU
properly.
2018-05-08 17:00:31 -04:00

80 lines
1.8 KiB
Go

package stats
import (
"context"
"fmt"
"math"
"sync"
"time"
multierror "github.com/hashicorp/go-multierror"
"github.com/shirou/gopsutil/cpu"
)
const (
// We use this constant to override the built in 3 second timeout in gopsutil
cpuInfoTimeout = 10 * time.Second
)
var (
cpuMhzPerCore float64
cpuModelName string
cpuNumCores int
cpuTotalTicks float64
initErr error
onceLer sync.Once
)
func Init() error {
onceLer.Do(func() {
var merrs *multierror.Error
var err error
if cpuNumCores, err = cpu.Counts(true); err != nil {
merrs = multierror.Append(merrs, fmt.Errorf("Unable to determine the number of CPU cores available: %v", err))
}
var cpuInfo []cpu.InfoStat
ctx, _ := context.WithTimeout(context.Background(), cpuInfoTimeout)
if cpuInfo, err = cpu.InfoWithContext(ctx); err != nil {
merrs = multierror.Append(merrs, fmt.Errorf("Unable to obtain CPU information: %v", initErr))
}
for _, cpu := range cpuInfo {
cpuModelName = cpu.ModelName
cpuMhzPerCore = cpu.Mhz
break
}
// Floor all of the values such that small difference don't cause the
// node to fall into a unique computed node class
cpuMhzPerCore = math.Floor(cpuMhzPerCore)
cpuTotalTicks = math.Floor(float64(cpuNumCores) * cpuMhzPerCore)
// Set any errors that occurred
initErr = merrs.ErrorOrNil()
})
return initErr
}
// CPUModelName returns the number of CPU cores available
func CPUNumCores() int {
return cpuNumCores
}
// CPUMHzPerCore returns the MHz per CPU core
func CPUMHzPerCore() float64 {
return cpuMhzPerCore
}
// CPUModelName returns the model name of the CPU
func CPUModelName() string {
return cpuModelName
}
// TotalTicksAvailable calculates the total Mhz available across all cores
func TotalTicksAvailable() float64 {
return cpuTotalTicks
}