Merge pull request #69 from monnand/per-cpu-usage-in-sample
per-core usage in sample
This commit is contained in:
commit
739142efe2
@ -119,7 +119,7 @@ type CpuStats struct {
|
|||||||
|
|
||||||
// Per CPU/core usage of the container.
|
// Per CPU/core usage of the container.
|
||||||
// Unit: nanoseconds.
|
// Unit: nanoseconds.
|
||||||
PerCpu []uint64 `json:"per_cpu,omitempty"`
|
PerCpu []uint64 `json:"per_cpu_usage,omitempty"`
|
||||||
|
|
||||||
// Time spent in user space.
|
// Time spent in user space.
|
||||||
// Unit: nanoseconds
|
// Unit: nanoseconds
|
||||||
@ -173,6 +173,9 @@ type ContainerStatsSample struct {
|
|||||||
Cpu struct {
|
Cpu struct {
|
||||||
// number of nanoseconds of CPU time used by the container
|
// number of nanoseconds of CPU time used by the container
|
||||||
Usage uint64 `json:"usage"`
|
Usage uint64 `json:"usage"`
|
||||||
|
|
||||||
|
// Per-core usage of the container. (unit: nanoseconds)
|
||||||
|
PerCpuUsage []uint64 `json:"per_cpu_usage,omitempty"`
|
||||||
} `json:"cpu"`
|
} `json:"cpu"`
|
||||||
Memory struct {
|
Memory struct {
|
||||||
// Units: Bytes.
|
// Units: Bytes.
|
||||||
@ -211,9 +214,28 @@ func NewSample(prev, current *ContainerStats) (*ContainerStatsSample, error) {
|
|||||||
if current.Cpu.Usage.Total < prev.Cpu.Usage.Total {
|
if current.Cpu.Usage.Total < prev.Cpu.Usage.Total {
|
||||||
return nil, fmt.Errorf("current CPU usage is less than prev CPU usage (cumulative).")
|
return nil, fmt.Errorf("current CPU usage is less than prev CPU usage (cumulative).")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var percpu []uint64
|
||||||
|
|
||||||
|
if len(current.Cpu.Usage.PerCpu) > 0 {
|
||||||
|
curNumCpus := len(current.Cpu.Usage.PerCpu)
|
||||||
|
percpu = make([]uint64, curNumCpus)
|
||||||
|
|
||||||
|
for i, currUsage := range current.Cpu.Usage.PerCpu {
|
||||||
|
var prevUsage uint64 = 0
|
||||||
|
if i < len(prev.Cpu.Usage.PerCpu) {
|
||||||
|
prevUsage = prev.Cpu.Usage.PerCpu[i]
|
||||||
|
}
|
||||||
|
if currUsage < prevUsage {
|
||||||
|
return nil, fmt.Errorf("current per-core CPU usage is less than prev per-core CPU usage (cumulative).")
|
||||||
|
}
|
||||||
|
percpu[i] = currUsage - prevUsage
|
||||||
|
}
|
||||||
|
}
|
||||||
sample := new(ContainerStatsSample)
|
sample := new(ContainerStatsSample)
|
||||||
// Calculate the diff to get the CPU usage within the time interval.
|
// Calculate the diff to get the CPU usage within the time interval.
|
||||||
sample.Cpu.Usage = current.Cpu.Usage.Total - prev.Cpu.Usage.Total
|
sample.Cpu.Usage = current.Cpu.Usage.Total - prev.Cpu.Usage.Total
|
||||||
|
sample.Cpu.PerCpuUsage = percpu
|
||||||
// Memory usage is current memory usage
|
// Memory usage is current memory usage
|
||||||
sample.Memory.Usage = current.Memory.Usage
|
sample.Memory.Usage = current.Memory.Usage
|
||||||
sample.Timestamp = current.Timestamp
|
sample.Timestamp = current.Timestamp
|
||||||
|
@ -230,3 +230,50 @@ func TestAddSampleWrongCpuUsage(t *testing.T) {
|
|||||||
t.Errorf("generated an unexpected sample: %+v", sample)
|
t.Errorf("generated an unexpected sample: %+v", sample)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestAddSampleHotPluggingCpu(t *testing.T) {
|
||||||
|
cpuPrevUsage := uint64(10)
|
||||||
|
cpuCurrentUsage := uint64(15)
|
||||||
|
memCurrentUsage := uint64(200)
|
||||||
|
prevTime := time.Now()
|
||||||
|
|
||||||
|
prev := createStats(cpuPrevUsage, memCurrentUsage, prevTime)
|
||||||
|
current := createStats(cpuCurrentUsage, memCurrentUsage, prevTime.Add(1*time.Second))
|
||||||
|
current.Cpu.Usage.PerCpu = append(current.Cpu.Usage.PerCpu, 10)
|
||||||
|
|
||||||
|
sample, err := NewSample(prev, current)
|
||||||
|
if err != nil {
|
||||||
|
t.Errorf("should be able to generate a sample. but received error: %v", err)
|
||||||
|
}
|
||||||
|
if len(sample.Cpu.PerCpuUsage) != 2 {
|
||||||
|
t.Fatalf("Should have 2 cores.")
|
||||||
|
}
|
||||||
|
if sample.Cpu.PerCpuUsage[0] != cpuCurrentUsage-cpuPrevUsage {
|
||||||
|
t.Errorf("First cpu usage is %v. should be %v", sample.Cpu.PerCpuUsage[0], cpuCurrentUsage-cpuPrevUsage)
|
||||||
|
}
|
||||||
|
if sample.Cpu.PerCpuUsage[1] != 10 {
|
||||||
|
t.Errorf("Second cpu usage is %v. should be 10", sample.Cpu.PerCpuUsage[1])
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestAddSampleHotUnpluggingCpu(t *testing.T) {
|
||||||
|
cpuPrevUsage := uint64(10)
|
||||||
|
cpuCurrentUsage := uint64(15)
|
||||||
|
memCurrentUsage := uint64(200)
|
||||||
|
prevTime := time.Now()
|
||||||
|
|
||||||
|
prev := createStats(cpuPrevUsage, memCurrentUsage, prevTime)
|
||||||
|
current := createStats(cpuCurrentUsage, memCurrentUsage, prevTime.Add(1*time.Second))
|
||||||
|
prev.Cpu.Usage.PerCpu = append(prev.Cpu.Usage.PerCpu, 10)
|
||||||
|
|
||||||
|
sample, err := NewSample(prev, current)
|
||||||
|
if err != nil {
|
||||||
|
t.Errorf("should be able to generate a sample. but received error: %v", err)
|
||||||
|
}
|
||||||
|
if len(sample.Cpu.PerCpuUsage) != 1 {
|
||||||
|
t.Fatalf("Should have 1 cores.")
|
||||||
|
}
|
||||||
|
if sample.Cpu.PerCpuUsage[0] != cpuCurrentUsage-cpuPrevUsage {
|
||||||
|
t.Errorf("First cpu usage is %v. should be %v", sample.Cpu.PerCpuUsage[0], cpuCurrentUsage-cpuPrevUsage)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@ -44,7 +44,7 @@ func buildTrace(cpu, mem []uint64, duration time.Duration) []*info.ContainerStat
|
|||||||
stats.Cpu.Usage.Total = cpuTotalUsage
|
stats.Cpu.Usage.Total = cpuTotalUsage
|
||||||
stats.Cpu.Usage.User = stats.Cpu.Usage.Total
|
stats.Cpu.Usage.User = stats.Cpu.Usage.Total
|
||||||
stats.Cpu.Usage.System = 0
|
stats.Cpu.Usage.System = 0
|
||||||
stats.Cpu.Usage.PerCpu = []uint64{cpuUsage}
|
stats.Cpu.Usage.PerCpu = []uint64{cpuTotalUsage}
|
||||||
|
|
||||||
stats.Memory.Usage = mem[i]
|
stats.Memory.Usage = mem[i]
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user