-
Notifications
You must be signed in to change notification settings - Fork 2.5k
Closed
Labels
Description
Host operating system: output of uname -a
This happens on CentOS 7, but looking at the code this is likely to happen on all operating systems.
node_exporter version: output of node_exporter --version
master at 4484f18 but also in older release versions
node_exporter command line flags
--collector.interrupts
node_exporter log output
level=error msg="ERROR: interrupts collector failed after 0.001310s: invalid value Rescheduling in interrupts: strconv.ParseFloat: parsing \"Rescheduling\": invalid syntax" source="collector.go:132"
Are you running node_exporter in Docker?
What did you do that produced an error?
The collector fails on this line of /proc/interrupts
:
IPI0:2768808080 2844211768 2878602432 2730576120 2723524623 3349096412 2717389879 2154252810 Rescheduling interrupts
What did you expect to see?
The name of the interrupt being set to IPI0
and the first value to 2768808080
.
What did you see instead?
The name of the interrupt being set to IPI0:276880808
and the first value to 2844211768
.
Further info
The error happens here: https://github.com/prometheus/node_exporter/blob/master/collector/interrupts_linux.go
With a copy of the problematic /proc/interrupts
saved as /tmp/interrupts
:
$ go run int.go
CPU Count: 8
Old: Can't parse value as float.
intName: IPI0:276880808
error: strconv.ParseFloat: parsing "Rescheduling": invalid syntax
parts: []string{"IPI0:2768808080", "2844211768", "2878602432", "2730576120", "2723524623", "3349096412", "2717389879", "2154252810", "Rescheduling", "interrupts"}
line: IPI0:2768808080 2844211768 2878602432 2730576120 2723524623 3349096412 2717389879 2154252810 Rescheduling interrupts
package main
import (
"bufio"
"fmt"
"os"
"strconv"
"strings"
)
func main() {
file, _ := os.Open("/tmp/interrupts")
scanner := bufio.NewScanner(file)
scanner.Scan()
cpuNum := len(strings.Fields(scanner.Text()))
fmt.Printf("CPU Count: %d\n", cpuNum)
for scanner.Scan() {
parts := strings.Fields(scanner.Text())
if len(parts) > 2 {
intName := parts[0][:len(parts[0])-1]
_, err := strconv.ParseFloat(parts[cpuNum], 64)
if err != nil {
fmt.Printf("Old: Can't parse value as float.\nintName: %s\nerror: %s\nparts: %#v\nline: %s\n",
intName, err, parts, scanner.Text())
}
}
p := strings.SplitN(scanner.Text(), ":", 2)
if len(p) > 1 {
parts = strings.Fields(p[1])
if len(parts) > 2 {
intName := p[0]
_, err := strconv.ParseFloat(parts[cpuNum-1], 64)
if err != nil {
fmt.Printf("New: Can't parse value as float.\nintName: %s\nerror: %s\nparts: %#v\nline: %s\n",
intName, err, parts, scanner.Text())
}
}
}
}
}
So it looks like first splitting the line on :
and then parsing it into fields might be a solution.