|
38 | 38 | ctx context.Context
|
39 | 39 | cancel context.CancelFunc
|
40 | 40 | wg sync.WaitGroup
|
41 |
| - cfgMaxProcs int |
42 |
| - lastMaxProcs int |
| 41 | + lastCPU int |
43 | 42 | lastMemoryLimit uint64
|
| 43 | + |
| 44 | + getCgroupCPUPeriodAndQuota = cgroup.GetCPUPeriodAndQuota |
| 45 | + getCgroupMemoryLimit = cgroup.GetMemoryLimit |
44 | 46 | )
|
45 | 47 |
|
46 | 48 | // StartCgroupMonitor uses to start the cgroup monitoring.
|
@@ -115,45 +117,44 @@ func refreshCgroupCPU() error {
|
115 | 117 | quota := runtime.NumCPU()
|
116 | 118 |
|
117 | 119 | // Get CPU quota from cgroup.
|
118 |
| - cpuPeriod, cpuQuota, err := cgroup.GetCPUPeriodAndQuota() |
119 |
| - if err != nil { |
120 |
| - return err |
121 |
| - } |
122 |
| - if cpuPeriod > 0 && cpuQuota > 0 { |
| 120 | + cpuPeriod, cpuQuota, err := getCgroupCPUPeriodAndQuota() |
| 121 | + |
| 122 | + // Only use cgroup CPU quota if it is available. It's possible that the cgroup doesn't have CPU quota set. |
| 123 | + // Then in some environments, systemd will not enable the cpu controller if cpu quota is not set. |
| 124 | + if err == nil && cpuPeriod > 0 && cpuQuota > 0 { |
123 | 125 | ratio := float64(cpuQuota) / float64(cpuPeriod)
|
124 | 126 | if ratio < float64(quota) {
|
125 | 127 | quota = int(math.Ceil(ratio))
|
126 | 128 | }
|
127 | 129 | }
|
128 | 130 |
|
129 |
| - if quota != lastMaxProcs { |
| 131 | + if quota != lastCPU { |
130 | 132 | log.Info("set the maxprocs", zap.Int("quota", quota))
|
131 | 133 | metrics.MaxProcs.Set(float64(quota))
|
132 |
| - lastMaxProcs = quota |
133 |
| - } else if lastMaxProcs == 0 { |
134 |
| - log.Info("set the maxprocs", zap.Int("cfgMaxProcs", cfgMaxProcs)) |
135 |
| - metrics.MaxProcs.Set(float64(cfgMaxProcs)) |
136 |
| - lastMaxProcs = cfgMaxProcs |
| 134 | + lastCPU = quota |
137 | 135 | }
|
138 |
| - return nil |
| 136 | + |
| 137 | + return err |
139 | 138 | }
|
140 | 139 |
|
141 | 140 | func refreshCgroupMemory() error {
|
142 |
| - memLimit, err := cgroup.GetMemoryLimit() |
143 |
| - if err != nil { |
144 |
| - return err |
145 |
| - } |
| 141 | + // Get the total memory limit from `procfs` |
146 | 142 | vmem, err := mem.VirtualMemory()
|
147 | 143 | if err != nil {
|
148 | 144 | return err
|
149 | 145 | }
|
150 |
| - if memLimit > vmem.Total { |
151 |
| - memLimit = vmem.Total |
| 146 | + memLimit := vmem.Total |
| 147 | + |
| 148 | + // Only use cgroup memory limit if it is available. |
| 149 | + cgroupMemLimit, err := getCgroupMemoryLimit() |
| 150 | + if err == nil && cgroupMemLimit < memLimit { |
| 151 | + memLimit = cgroupMemLimit |
152 | 152 | }
|
| 153 | + |
153 | 154 | if memLimit != lastMemoryLimit {
|
154 | 155 | log.Info("set the memory limit", zap.Uint64("memLimit", memLimit))
|
155 | 156 | metrics.MemoryLimit.Set(float64(memLimit))
|
156 | 157 | lastMemoryLimit = memLimit
|
157 | 158 | }
|
158 |
| - return nil |
| 159 | + return err |
159 | 160 | }
|
0 commit comments