Merge pull request #16 from shirou/errorhandling

Errorhandling
pull/17/head
shirou 11 years ago
commit 0cdfc73bfa

@ -32,11 +32,26 @@ func CPUTimes(percpu bool) ([]CPUTimesStat, error) {
return ret, err return ret, err
} }
user, _ := strconv.ParseFloat(cpuTime[CPUser], 32) user, err := strconv.ParseFloat(cpuTime[CPUser], 32)
nice, _ := strconv.ParseFloat(cpuTime[CPNice], 32) if err != nil {
sys, _ := strconv.ParseFloat(cpuTime[CPSys], 32) return ret, err
idle, _ := strconv.ParseFloat(cpuTime[CPIdle], 32) }
intr, _ := strconv.ParseFloat(cpuTime[CPIntr], 32) nice, err := strconv.ParseFloat(cpuTime[CPNice], 32)
if err != nil {
return ret, err
}
sys, err := strconv.ParseFloat(cpuTime[CPSys], 32)
if err != nil {
return ret, err
}
idle, err := strconv.ParseFloat(cpuTime[CPIdle], 32)
if err != nil {
return ret, err
}
intr, err := strconv.ParseFloat(cpuTime[CPIntr], 32)
if err != nil {
return ret, err
}
c := CPUTimesStat{ c := CPUTimesStat{
User: float32(user / ClocksPerSec), User: float32(user / ClocksPerSec),
@ -64,6 +79,10 @@ func CPUInfo() ([]CPUInfoStat, error) {
for _, line := range strings.Split(string(out), "\n") { for _, line := range strings.Split(string(out), "\n") {
values := strings.Fields(line) values := strings.Fields(line)
t, err := strconv.ParseInt(values[1], 10, 32)
if err != nil {
return ret, err
}
if strings.HasPrefix(line, "machdep.cpu.brand_string") { if strings.HasPrefix(line, "machdep.cpu.brand_string") {
c.ModelName = strings.Join(values[1:], " ") c.ModelName = strings.Join(values[1:], " ")
} else if strings.HasPrefix(line, "machdep.cpu.family") { } else if strings.HasPrefix(line, "machdep.cpu.family") {
@ -71,7 +90,7 @@ func CPUInfo() ([]CPUInfoStat, error) {
} else if strings.HasPrefix(line, "machdep.cpu.model") { } else if strings.HasPrefix(line, "machdep.cpu.model") {
c.Model = values[1] c.Model = values[1]
} else if strings.HasPrefix(line, "machdep.cpu.stepping") { } else if strings.HasPrefix(line, "machdep.cpu.stepping") {
c.Stepping = mustParseInt32(values[1]) c.Stepping = int32(t)
} else if strings.HasPrefix(line, "machdep.cpu.features") { } else if strings.HasPrefix(line, "machdep.cpu.features") {
for _, v := range values[1:] { for _, v := range values[1:] {
c.Flags = append(c.Flags, strings.ToLower(v)) c.Flags = append(c.Flags, strings.ToLower(v))
@ -85,9 +104,9 @@ func CPUInfo() ([]CPUInfoStat, error) {
c.Flags = append(c.Flags, strings.ToLower(v)) c.Flags = append(c.Flags, strings.ToLower(v))
} }
} else if strings.HasPrefix(line, "machdep.cpu.core_count") { } else if strings.HasPrefix(line, "machdep.cpu.core_count") {
c.Cores = mustParseInt32(values[1]) c.Cores = int32(t)
} else if strings.HasPrefix(line, "machdep.cpu.cache.size") { } else if strings.HasPrefix(line, "machdep.cpu.cache.size") {
c.CacheSize = mustParseInt32(values[1]) c.CacheSize = int32(t)
} else if strings.HasPrefix(line, "machdep.cpu.vendor") { } else if strings.HasPrefix(line, "machdep.cpu.vendor") {
c.VendorID = values[1] c.VendorID = values[1]
} }

@ -32,11 +32,26 @@ func CPUTimes(percpu bool) ([]CPUTimesStat, error) {
return ret, err return ret, err
} }
user, _ := strconv.ParseFloat(cpuTime[CPUser], 32) user, err := strconv.ParseFloat(cpuTime[CPUser], 32)
nice, _ := strconv.ParseFloat(cpuTime[CPNice], 32) if err != nil {
sys, _ := strconv.ParseFloat(cpuTime[CPSys], 32) return ret, err
idle, _ := strconv.ParseFloat(cpuTime[CPIdle], 32) }
intr, _ := strconv.ParseFloat(cpuTime[CPIntr], 32) nice, err := strconv.ParseFloat(cpuTime[CPNice], 32)
if err != nil {
return ret, err
}
sys, err := strconv.ParseFloat(cpuTime[CPSys], 32)
if err != nil {
return ret, err
}
idle, err := strconv.ParseFloat(cpuTime[CPIdle], 32)
if err != nil {
return ret, err
}
intr, err := strconv.ParseFloat(cpuTime[CPIntr], 32)
if err != nil {
return ret, err
}
c := CPUTimesStat{ c := CPUTimesStat{
User: float32(user / ClocksPerSec), User: float32(user / ClocksPerSec),
@ -62,12 +77,20 @@ func CPUInfo() ([]CPUInfoStat, error) {
for _, line := range lines { for _, line := range lines {
if matches := regexp.MustCompile(`CPU:\s+(.+) \(([\d.]+).+\)`).FindStringSubmatch(line); matches != nil { if matches := regexp.MustCompile(`CPU:\s+(.+) \(([\d.]+).+\)`).FindStringSubmatch(line); matches != nil {
c.ModelName = matches[1] c.ModelName = matches[1]
c.Mhz = mustParseFloat64(matches[2]) t, err := strconv.ParseFloat(matches[2], 64)
if err != nil {
return ret, nil
}
c.Mhz = t
} else if matches := regexp.MustCompile(`Origin = "(.+)" Id = (.+) Family = (.+) Model = (.+) Stepping = (.+)`).FindStringSubmatch(line); matches != nil { } else if matches := regexp.MustCompile(`Origin = "(.+)" Id = (.+) Family = (.+) Model = (.+) Stepping = (.+)`).FindStringSubmatch(line); matches != nil {
c.VendorID = matches[1] c.VendorID = matches[1]
c.Family = matches[3] c.Family = matches[3]
c.Model = matches[4] c.Model = matches[4]
c.Stepping = mustParseInt32(matches[5]) t, err := strconv.ParseInt(matches[5], 10, 32)
if err != nil {
return ret, nil
}
c.Stepping = int32(t)
} else if matches := regexp.MustCompile(`Features=.+<(.+)>`).FindStringSubmatch(line); matches != nil { } else if matches := regexp.MustCompile(`Features=.+<(.+)>`).FindStringSubmatch(line); matches != nil {
for _, v := range strings.Split(matches[1], ",") { for _, v := range strings.Split(matches[1], ",") {
c.Flags = append(c.Flags, strings.ToLower(v)) c.Flags = append(c.Flags, strings.ToLower(v))
@ -78,7 +101,11 @@ func CPUInfo() ([]CPUInfoStat, error) {
} }
} else if matches := regexp.MustCompile(`Logical CPUs per core: (\d+)`).FindStringSubmatch(line); matches != nil { } else if matches := regexp.MustCompile(`Logical CPUs per core: (\d+)`).FindStringSubmatch(line); matches != nil {
// FIXME: no this line? // FIXME: no this line?
c.Cores = mustParseInt32(matches[1]) t, err := strconv.ParseInt(matches[1], 10, 32)
if err != nil {
return ret, nil
}
c.Cores = int32(t)
} }
} }

@ -46,7 +46,11 @@ func CPUInfo() ([]CPUInfoStat, error) {
switch key { switch key {
case "processor": case "processor":
c = CPUInfoStat{} c = CPUInfoStat{}
c.CPU = mustParseInt32(value) t, err := strconv.ParseInt(value, 10, 32)
if err != nil {
return ret, err
}
c.CPU = int32(t)
case "vendor_id": case "vendor_id":
c.VendorID = value c.VendorID = value
case "cpu family": case "cpu family":
@ -56,17 +60,33 @@ func CPUInfo() ([]CPUInfoStat, error) {
case "model name": case "model name":
c.ModelName = value c.ModelName = value
case "stepping": case "stepping":
c.Stepping = mustParseInt32(value) t, err := strconv.ParseInt(value, 10, 32)
if err != nil {
return ret, err
}
c.Stepping = int32(t)
case "cpu MHz": case "cpu MHz":
c.Mhz = mustParseFloat64(value) t, err := strconv.ParseFloat(value, 64)
if err != nil {
return ret, err
}
c.Mhz = t
case "cache size": case "cache size":
c.CacheSize = mustParseInt32(strings.Replace(value, " KB", "", 1)) t, err := strconv.ParseInt(strings.Replace(value, " KB", "", 1), 10, 32)
if err != nil {
return ret, err
}
c.CacheSize = int32(t)
case "physical id": case "physical id":
c.PhysicalID = value c.PhysicalID = value
case "core id": case "core id":
c.CoreID = value c.CoreID = value
case "cpu cores": case "cpu cores":
c.Cores = mustParseInt32(value) t, err := strconv.ParseInt(value, 10, 32)
if err != nil {
return ret, err
}
c.Cores = int32(t)
case "flags": case "flags":
c.Flags = strings.Split(value, ",") c.Flags = strings.Split(value, ",")
} }
@ -86,14 +106,38 @@ func parseStatLine(line string) (*CPUTimesStat, error) {
if cpu == "cpu" { if cpu == "cpu" {
cpu = "cpu-total" cpu = "cpu-total"
} }
user, _ := strconv.ParseFloat(fields[1], 32) user, err := strconv.ParseFloat(fields[1], 32)
nice, _ := strconv.ParseFloat(fields[2], 32) if err != nil {
system, _ := strconv.ParseFloat(fields[3], 32) return nil, err
idle, _ := strconv.ParseFloat(fields[4], 32) }
iowait, _ := strconv.ParseFloat(fields[5], 32) nice, err := strconv.ParseFloat(fields[2], 32)
irq, _ := strconv.ParseFloat(fields[6], 32) if err != nil {
softirq, _ := strconv.ParseFloat(fields[7], 32) return nil, err
stolen, _ := strconv.ParseFloat(fields[8], 32) }
system, err := strconv.ParseFloat(fields[3], 32)
if err != nil {
return nil, err
}
idle, err := strconv.ParseFloat(fields[4], 32)
if err != nil {
return nil, err
}
iowait, err := strconv.ParseFloat(fields[5], 32)
if err != nil {
return nil, err
}
irq, err := strconv.ParseFloat(fields[6], 32)
if err != nil {
return nil, err
}
softirq, err := strconv.ParseFloat(fields[7], 32)
if err != nil {
return nil, err
}
stolen, err := strconv.ParseFloat(fields[8], 32)
if err != nil {
return nil, err
}
ct := &CPUTimesStat{ ct := &CPUTimesStat{
CPU: cpu, CPU: cpu,
User: float32(user), User: float32(user),
@ -106,15 +150,24 @@ func parseStatLine(line string) (*CPUTimesStat, error) {
Stolen: float32(stolen), Stolen: float32(stolen),
} }
if len(fields) > 9 { // Linux >= 2.6.11 if len(fields) > 9 { // Linux >= 2.6.11
steal, _ := strconv.ParseFloat(fields[9], 32) steal, err := strconv.ParseFloat(fields[9], 32)
if err != nil {
return nil, err
}
ct.Steal = float32(steal) ct.Steal = float32(steal)
} }
if len(fields) > 10 { // Linux >= 2.6.24 if len(fields) > 10 { // Linux >= 2.6.24
guest, _ := strconv.ParseFloat(fields[10], 32) guest, err := strconv.ParseFloat(fields[10], 32)
if err != nil {
return nil, err
}
ct.Guest = float32(guest) ct.Guest = float32(guest)
} }
if len(fields) > 11 { // Linux >= 3.2.0 if len(fields) > 11 { // Linux >= 3.2.0
guestNice, _ := strconv.ParseFloat(fields[11], 32) guestNice, err := strconv.ParseFloat(fields[11], 32)
if err != nil {
return nil, err
}
ct.GuestNice = float32(guestNice) ct.GuestNice = float32(guestNice)
} }

@ -31,7 +31,7 @@ type DiskIOCountersStat struct {
ReadTime uint64 `json:"readTime"` ReadTime uint64 `json:"readTime"`
WriteTime uint64 `json:"writeTime"` WriteTime uint64 `json:"writeTime"`
Name string `json:"name"` Name string `json:"name"`
IoTime uint64 `json:"ioTime"` IoTime uint64 `json:"ioTime"`
} }
func (d DiskUsageStat) String() string { func (d DiskUsageStat) String() string {

@ -3,6 +3,7 @@
package gopsutil package gopsutil
import ( import (
"strconv"
"strings" "strings"
) )
@ -25,7 +26,7 @@ func DiskPartitions(all bool) ([]DiskPartitionStat, error) {
for _, line := range lines { for _, line := range lines {
fields := strings.Fields(line) fields := strings.Fields(line)
d := DiskPartitionStat{ d := DiskPartitionStat{
Device: fields[0], Device: fields[0],
Mountpoint: fields[1], Mountpoint: fields[1],
Fstype: fields[2], Fstype: fields[2],
Opts: fields[3], Opts: fields[3],
@ -48,13 +49,34 @@ func DiskIOCounters() (map[string]DiskIOCountersStat, error) {
for _, line := range lines { for _, line := range lines {
fields := strings.Fields(line) fields := strings.Fields(line)
name := fields[2] name := fields[2]
reads := mustParseUint64(fields[3]) reads, err := strconv.ParseUint((fields[3]), 10, 64)
rbytes := mustParseUint64(fields[5]) if err != nil {
rtime := mustParseUint64(fields[6]) return ret, err
writes := mustParseUint64(fields[7]) }
wbytes := mustParseUint64(fields[9]) rbytes, err := strconv.ParseUint((fields[5]), 10, 64)
wtime := mustParseUint64(fields[10]) if err != nil {
iotime := mustParseUint64(fields[12]) return ret, err
}
rtime, err := strconv.ParseUint((fields[6]), 10, 64)
if err != nil {
return ret, err
}
writes, err := strconv.ParseUint((fields[7]), 10, 64)
if err != nil {
return ret, err
}
wbytes, err := strconv.ParseUint((fields[9]), 10, 64)
if err != nil {
return ret, err
}
wtime, err := strconv.ParseUint((fields[10]), 10, 64)
if err != nil {
return ret, err
}
iotime, err := strconv.ParseUint((fields[12]), 10, 64)
if err != nil {
return ret, err
}
d := DiskIOCountersStat{ d := DiskIOCountersStat{
ReadBytes: rbytes * SectorSize, ReadBytes: rbytes * SectorSize,
WriteBytes: wbytes * SectorSize, WriteBytes: wbytes * SectorSize,
@ -62,7 +84,7 @@ func DiskIOCounters() (map[string]DiskIOCountersStat, error) {
WriteCount: writes, WriteCount: writes,
ReadTime: rtime, ReadTime: rtime,
WriteTime: wtime, WriteTime: wtime,
IoTime: iotime, IoTime: iotime,
} }
if d == empty { if d == empty {
continue continue

@ -60,7 +60,11 @@ func HostInfo() (*HostInfoStat, error) {
if err == nil { if err == nil {
// ex: { sec = 1392261637, usec = 627534 } Thu Feb 13 12:20:37 2014 // ex: { sec = 1392261637, usec = 627534 } Thu Feb 13 12:20:37 2014
v := strings.Replace(values[2], ",", "", 1) v := strings.Replace(values[2], ",", "", 1)
ret.Uptime = mustParseUint64(v) t, err := strconv.ParseUint(v, 10, 64)
if err != nil {
return ret, err
}
ret.Uptime = t
} }
return ret, nil return ret, nil

@ -42,7 +42,11 @@ func HostInfo() (*HostInfoStat, error) {
if err == nil { if err == nil {
// ex: { sec = 1392261637, usec = 627534 } Thu Feb 13 12:20:37 2014 // ex: { sec = 1392261637, usec = 627534 } Thu Feb 13 12:20:37 2014
v := strings.Replace(values[2], ",", "", 1) v := strings.Replace(values[2], ",", "", 1)
ret.Uptime = mustParseUint64(v) t, err := strconv.ParseUint(v, 10, 64)
if err != nil {
return ret, err
}
ret.Uptime = t
} }
return ret, nil return ret, nil

@ -4,6 +4,7 @@ package gopsutil
import ( import (
"os/exec" "os/exec"
"strconv"
"strings" "strings"
) )
@ -12,34 +13,46 @@ func getPageSize() (uint64, error) {
if err != nil { if err != nil {
return 0, err return 0, err
} }
p := mustParseUint64(string(out)) o := strings.TrimSpace(string(out))
p, err := strconv.ParseUint(o, 10, 64)
if err != nil {
return 0, err
}
return p, nil return p, nil
} }
// VirtualMemory returns VirtualmemoryStat. // VirtualMemory returns VirtualmemoryStat.
func VirtualMemory() (*VirtualMemoryStat, error) { func VirtualMemory() (*VirtualMemoryStat, error) {
p, _ := getPageSize() p, err := getPageSize()
if err != nil {
total, _ := doSysctrl("hw.memsize") return nil, err
free, _ := doSysctrl("vm.page_free_count") }
/*
active, _ := doSysctrl("vm.stats.vm.v_active_count") total, err := doSysctrl("hw.memsize")
inactive, _ := doSysctrl("vm.pageout_inactive_used") if err != nil {
cache, _ := doSysctrl("vm.stats.vm.v_cache_count") return nil, err
buffer, _ := doSysctrl("vfs.bufspace") }
wired, _ := doSysctrl("vm.stats.vm.v_wire_count") free, err := doSysctrl("vm.page_free_count")
*/ if err != nil {
return nil, err
}
parsed := make([]uint64, 0, 7)
vv := []string{
total[0],
free[0],
}
for _, target := range vv {
t, err := strconv.ParseUint(target, 10, 64)
if err != nil {
return nil, err
}
parsed = append(parsed, t)
}
ret := &VirtualMemoryStat{ ret := &VirtualMemoryStat{
Total: mustParseUint64(total[0]) * p, Total: parsed[0] * p,
Free: mustParseUint64(free[0]) * p, Free: parsed[1] * p,
/*
Active: mustParseUint64(active[0]) * p,
Inactive: mustParseUint64(inactive[0]) * p,
Cached: mustParseUint64(cache[0]) * p,
Buffers: mustParseUint64(buffer[0]),
Wired: mustParseUint64(wired[0]) * p,
*/
} }
// TODO: platform independent (worked freebsd?) // TODO: platform independent (worked freebsd?)
@ -53,21 +66,38 @@ func VirtualMemory() (*VirtualMemoryStat, error) {
// SwapMemory returns swapinfo. // SwapMemory returns swapinfo.
func SwapMemory() (*SwapMemoryStat, error) { func SwapMemory() (*SwapMemoryStat, error) {
swapUsage, _ := doSysctrl("vm.swapusage")
var ret *SwapMemoryStat var ret *SwapMemoryStat
total := strings.Replace(swapUsage[3], "M", "", 1) swapUsage, err := doSysctrl("vm.swapusage")
used := strings.Replace(swapUsage[6], "M", "", 1) if err != nil {
free := strings.Replace(swapUsage[9], "M", "", 1) return ret, err
}
total := strings.Replace(swapUsage[2], "M", "", 1)
used := strings.Replace(swapUsage[5], "M", "", 1)
free := strings.Replace(swapUsage[8], "M", "", 1)
total_v, err := strconv.ParseFloat(total, 64)
if err != nil {
return nil, err
}
used_v, err := strconv.ParseFloat(used, 64)
if err != nil {
return nil, err
}
free_v, err := strconv.ParseFloat(free, 64)
if err != nil {
return nil, err
}
u := "0" u := ((total_v - free_v) / total_v) * 100.0
// vm.swapusage shows "M", multiply 1000
ret = &SwapMemoryStat{ ret = &SwapMemoryStat{
Total: mustParseUint64(total), Total: uint64(total_v * 1000),
Used: mustParseUint64(used), Used: uint64(used_v * 1000),
Free: mustParseUint64(free), Free: uint64(free_v * 1000),
UsedPercent: mustParseFloat64(u), UsedPercent: u,
} }
return ret, nil return ret, nil

@ -4,30 +4,75 @@ package gopsutil
import ( import (
"os/exec" "os/exec"
"strconv"
"strings" "strings"
) )
func VirtualMemory() (*VirtualMemoryStat, error) { func VirtualMemory() (*VirtualMemoryStat, error) {
pageSize, err := doSysctrl("vm.stats.vm.v_page_size")
if err != nil {
return nil, err
}
p, err := strconv.ParseUint(pageSize[0], 10, 64)
if err != nil {
return nil, err
}
pageSize, _ := doSysctrl("vm.stats.vm.v_page_size") pageCount, err := doSysctrl("vm.stats.vm.v_page_count")
p := mustParseUint64(pageSize[0]) if err != nil {
return nil, err
}
free, err := doSysctrl("vm.stats.vm.v_free_count")
if err != nil {
return nil, err
}
active, err := doSysctrl("vm.stats.vm.v_active_count")
if err != nil {
return nil, err
}
inactive, err := doSysctrl("vm.stats.vm.v_inactive_count")
if err != nil {
return nil, err
}
cache, err := doSysctrl("vm.stats.vm.v_cache_count")
if err != nil {
return nil, err
}
buffer, err := doSysctrl("vfs.bufspace")
if err != nil {
return nil, err
}
wired, err := doSysctrl("vm.stats.vm.v_wire_count")
if err != nil {
return nil, err
}
pageCount, _ := doSysctrl("vm.stats.vm.v_page_count") parsed := make([]uint64, 0, 7)
free, _ := doSysctrl("vm.stats.vm.v_free_count") vv := []string{
active, _ := doSysctrl("vm.stats.vm.v_active_count") pageCount[0],
inactive, _ := doSysctrl("vm.stats.vm.v_inactive_count") free[0],
cache, _ := doSysctrl("vm.stats.vm.v_cache_count") active[0],
buffer, _ := doSysctrl("vfs.bufspace") inactive[0],
wired, _ := doSysctrl("vm.stats.vm.v_wire_count") cache[0],
buffer[0],
wired[0],
}
for _, target := range vv {
t, err := strconv.ParseUint(target, 10, 64)
if err != nil {
return nil, err
}
parsed = append(parsed, t)
}
ret := &VirtualMemoryStat{ ret := &VirtualMemoryStat{
Total: mustParseUint64(pageCount[0]) * p, Total: parsed[0] * p,
Free: mustParseUint64(free[0]) * p, Free: parsed[1] * p,
Active: mustParseUint64(active[0]) * p, Active: parsed[2] * p,
Inactive: mustParseUint64(inactive[0]) * p, Inactive: parsed[3] * p,
Cached: mustParseUint64(cache[0]) * p, Cached: parsed[4] * p,
Buffers: mustParseUint64(buffer[0]), Buffers: parsed[5],
Wired: mustParseUint64(wired[0]) * p, Wired: parsed[6] * p,
} }
// TODO: platform independent (worked freebsd?) // TODO: platform independent (worked freebsd?)
@ -55,12 +100,28 @@ func SwapMemory() (*SwapMemoryStat, error) {
} }
u := strings.Replace(values[4], "%", "", 1) u := strings.Replace(values[4], "%", "", 1)
total_v, err := strconv.ParseUint(values[1], 10, 64)
if err != nil {
return nil, err
}
used_v, err := strconv.ParseUint(values[2], 10, 64)
if err != nil {
return nil, err
}
free_v, err := strconv.ParseUint(values[3], 10, 64)
if err != nil {
return nil, err
}
up_v, err := strconv.ParseFloat(u, 64)
if err != nil {
return nil, err
}
ret = &SwapMemoryStat{ ret = &SwapMemoryStat{
Total: mustParseUint64(values[1]), Total: total_v,
Used: mustParseUint64(values[2]), Used: used_v,
Free: mustParseUint64(values[3]), Free: free_v,
UsedPercent: mustParseFloat64(u), UsedPercent: up_v,
} }
} }

@ -3,6 +3,7 @@
package gopsutil package gopsutil
import ( import (
"strconv"
"strings" "strings"
"syscall" "syscall"
) )
@ -21,20 +22,23 @@ func VirtualMemory() (*VirtualMemoryStat, error) {
value := strings.TrimSpace(fields[1]) value := strings.TrimSpace(fields[1])
value = strings.Replace(value, " kB", "", -1) value = strings.Replace(value, " kB", "", -1)
t, err := strconv.ParseUint(value, 10, 64)
if err != nil {
return ret, err
}
switch key { switch key {
case "MemTotal": case "MemTotal":
ret.Total = mustParseUint64(value) * 1000 ret.Total = t * 1000
case "MemFree": case "MemFree":
ret.Free = mustParseUint64(value) * 1000 ret.Free = t * 1000
case "Buffers": case "Buffers":
ret.Buffers = mustParseUint64(value) * 1000 ret.Buffers = t * 1000
case "Cached": case "Cached":
ret.Cached = mustParseUint64(value) * 1000 ret.Cached = t * 1000
case "Active": case "Active":
ret.Active = mustParseUint64(value) * 1000 ret.Active = t * 1000
case "Inactive": case "Inactive":
ret.Inactive = mustParseUint64(value) * 1000 ret.Inactive = t * 1000
} }
} }
ret.Available = ret.Free + ret.Buffers + ret.Cached ret.Available = ret.Free + ret.Buffers + ret.Cached

@ -10,7 +10,6 @@ func TestVirtual_memory(t *testing.T) {
if err != nil { if err != nil {
t.Errorf("error %v", err) t.Errorf("error %v", err)
} }
empty := &VirtualMemoryStat{} empty := &VirtualMemoryStat{}
if v == empty { if v == empty {
t.Errorf("error %v", v) t.Errorf("error %v", v)

@ -4,6 +4,7 @@ package gopsutil
import ( import (
"os/exec" "os/exec"
"strconv"
"strings" "strings"
) )
@ -19,26 +20,39 @@ func NetIOCounters(pernic bool) ([]NetIOCountersStat, error) {
for _, line := range lines { for _, line := range lines {
values := strings.Fields(line) values := strings.Fields(line)
if len(values) < 1 || values[0] == "Name" { if len(values) < 1 || values[0] == "Name" {
// skip first line
continue continue
} }
base := 1 base := 1
// sometimes Address is ommitted // sometimes Address is ommitted
if len(values) < 13 { if len(values) < 11 {
base = 0 base = 0
} }
parsed := make([]uint64, 0, 3)
vv := []string{
values[base+3], // PacketsRecv
values[base+4], // Errin
values[base+5], // Dropin
}
for _, target := range vv {
if target == "-" {
parsed = append(parsed, 0)
continue
}
t, err := strconv.ParseUint(target, 10, 64)
if err != nil {
return nil, err
}
parsed = append(parsed, t)
}
n := NetIOCountersStat{ n := NetIOCountersStat{
Name: values[0], Name: values[0],
PacketsRecv: mustParseUint64(values[base+3]), PacketsRecv: parsed[0],
Errin: mustParseUint64(values[base+4]), Errin: parsed[1],
Dropin: mustParseUint64(values[base+5]), Dropin: parsed[2],
/*
BytesRecv: mustParseUint64(values[base+6]),
PacketsSent: mustParseUint64(values[base+7]),
Errout: mustParseUint64(values[base+8]),
BytesSent: mustParseUint64(values[base+9]),
Dropout: mustParseUint64(values[base+11]),
*/
} }
ret = append(ret, n) ret = append(ret, n)
} }

@ -4,6 +4,7 @@ package gopsutil
import ( import (
"os/exec" "os/exec"
"strconv"
"strings" "strings"
) )
@ -27,16 +28,40 @@ func NetIOCounters(pernic bool) ([]NetIOCountersStat, error) {
base = 0 base = 0
} }
parsed := make([]uint64, 0, 8)
vv := []string{
values[base+3], // PacketsRecv
values[base+4], // Errin
values[base+5], // Dropin
values[base+6], // BytesRecvn
values[base+7], // PacketSent
values[base+8], // Errout
values[base+9], // BytesSent
values[base+11], // Dropout
}
for _, target := range vv {
if target == "-" {
parsed = append(parsed, 0)
continue
}
t, err := strconv.ParseUint(target, 10, 64)
if err != nil {
return nil, err
}
parsed = append(parsed, t)
}
n := NetIOCountersStat{ n := NetIOCountersStat{
Name: values[0], Name: values[0],
PacketsRecv: mustParseUint64(values[base+3]), PacketsRecv: parsed[0],
Errin: mustParseUint64(values[base+4]), Errin: parsed[1],
Dropin: mustParseUint64(values[base+5]), Dropin: parsed[2],
BytesRecv: mustParseUint64(values[base+6]), BytesRecv: parsed[3],
PacketsSent: mustParseUint64(values[base+7]), PacketsSent: parsed[4],
Errout: mustParseUint64(values[base+8]), Errout: parsed[5],
BytesSent: mustParseUint64(values[base+9]), BytesSent: parsed[6],
Dropout: mustParseUint64(values[base+11]), Dropout: parsed[7],
} }
ret = append(ret, n) ret = append(ret, n)
} }

@ -3,6 +3,7 @@
package gopsutil package gopsutil
import ( import (
"strconv"
"strings" "strings"
) )
@ -22,16 +23,50 @@ func NetIOCounters(pernic bool) ([]NetIOCountersStat, error) {
if fields[0] == "" { if fields[0] == "" {
continue continue
} }
bytesRecv, err := strconv.ParseUint(fields[1], 10, 64)
if err != nil {
return ret, err
}
packetsRecv, err := strconv.ParseUint(fields[2], 10, 64)
if err != nil {
return ret, err
}
errIn, err := strconv.ParseUint(fields[3], 10, 64)
if err != nil {
return ret, err
}
dropIn, err := strconv.ParseUint(fields[4], 10, 64)
if err != nil {
return ret, err
}
bytesSent, err := strconv.ParseUint(fields[9], 10, 64)
if err != nil {
return ret, err
}
packetsSent, err := strconv.ParseUint(fields[10], 10, 64)
if err != nil {
return ret, err
}
errOut, err := strconv.ParseUint(fields[11], 10, 64)
if err != nil {
return ret, err
}
dropOut, err := strconv.ParseUint(fields[14], 10, 64)
if err != nil {
return ret, err
}
nic := NetIOCountersStat{ nic := NetIOCountersStat{
Name: strings.Trim(fields[0], ":"), Name: strings.Trim(fields[0], ":"),
BytesRecv: mustParseUint64(fields[1]), BytesRecv: bytesRecv,
PacketsRecv: mustParseUint64(fields[2]), PacketsRecv: packetsRecv,
Errin: mustParseUint64(fields[3]), Errin: errIn,
Dropin: mustParseUint64(fields[4]), Dropin: dropIn,
BytesSent: mustParseUint64(fields[9]), BytesSent: bytesSent,
PacketsSent: mustParseUint64(fields[10]), PacketsSent: packetsSent,
Errout: mustParseUint64(fields[11]), Errout: errOut,
Dropout: mustParseUint64(fields[12]), Dropout: dropOut,
} }
ret = append(ret, nic) ret = append(ret, nic)
} }

@ -5,13 +5,13 @@ import (
) )
type Process struct { type Process struct {
Pid int32 `json:"pid"` Pid int32 `json:"pid"`
name string name string
status string status string
numCtxSwitches *NumCtxSwitchesStat numCtxSwitches *NumCtxSwitchesStat
uids []int32 uids []int32
gids []int32 gids []int32
numThreads int32 numThreads int32
} }
type OpenFilesStat struct { type OpenFilesStat struct {

@ -195,7 +195,7 @@ func (p *Process) MemoryMaps(grouped bool) (*[]MemoryMapsStat, error) {
lines := strings.Split(string(contents), "\n") lines := strings.Split(string(contents), "\n")
// function of parsing a block // function of parsing a block
getBlock := func(first_line []string, block []string) MemoryMapsStat { getBlock := func(first_line []string, block []string) (MemoryMapsStat, error) {
m := MemoryMapsStat{} m := MemoryMapsStat{}
m.Path = first_line[len(first_line)-1] m.Path = first_line[len(first_line)-1]
@ -205,30 +205,35 @@ func (p *Process) MemoryMaps(grouped bool) (*[]MemoryMapsStat, error) {
continue continue
} }
v := strings.Trim(field[1], " kB") // remove last "kB" v := strings.Trim(field[1], " kB") // remove last "kB"
t, err := strconv.ParseUint(v, 10, 64)
if err != nil {
return m, err
}
switch field[0] { switch field[0] {
case "Size": case "Size":
m.Size = mustParseUint64(v) m.Size = t
case "Rss": case "Rss":
m.Rss = mustParseUint64(v) m.Rss = t
case "Pss": case "Pss":
m.Pss = mustParseUint64(v) m.Pss = t
case "Shared_Clean": case "Shared_Clean":
m.SharedClean = mustParseUint64(v) m.SharedClean = t
case "Shared_Dirty": case "Shared_Dirty":
m.SharedDirty = mustParseUint64(v) m.SharedDirty = t
case "Private_Clean": case "Private_Clean":
m.PrivateClean = mustParseUint64(v) m.PrivateClean = t
case "Private_Dirty": case "Private_Dirty":
m.PrivateDirty = mustParseUint64(v) m.PrivateDirty = t
case "Referenced": case "Referenced":
m.Referenced = mustParseUint64(v) m.Referenced = t
case "Anonymous": case "Anonymous":
m.Anonymous = mustParseUint64(v) m.Anonymous = t
case "Swap": case "Swap":
m.Swap = mustParseUint64(v) m.Swap = t
} }
} }
return m return m, nil
} }
blocks := make([]string, 16) blocks := make([]string, 16)
@ -237,7 +242,11 @@ func (p *Process) MemoryMaps(grouped bool) (*[]MemoryMapsStat, error) {
if strings.HasSuffix(field[0], ":") == false { if strings.HasSuffix(field[0], ":") == false {
// new block section // new block section
if len(blocks) > 0 { if len(blocks) > 0 {
ret = append(ret, getBlock(field, blocks)) g, err := getBlock(field, blocks)
if err != nil {
return &ret, err
}
ret = append(ret, g)
} }
// starts new block // starts new block
blocks = make([]string, 16) blocks = make([]string, 16)
@ -272,9 +281,13 @@ func (p *Process) fillFromfd() (int32, []*OpenFilesStat, error) {
if err != nil { if err != nil {
continue continue
} }
t, err := strconv.ParseUint(fd, 10, 64)
if err != nil {
return numFDs, openfiles, err
}
o := &OpenFilesStat{ o := &OpenFilesStat{
Path: filepath, Path: filepath,
Fd: mustParseUint64(fd), Fd: t,
} }
openfiles = append(openfiles, o) openfiles = append(openfiles, o)
} }
@ -338,15 +351,20 @@ func (p *Process) fillFromIO() (*IOCountersStat, error) {
if len(field) < 2 { if len(field) < 2 {
continue continue
} }
t, err := strconv.ParseInt(strings.Trim(field[1], " \t"), 10, 32)
if err != nil {
return nil, err
}
switch field[0] { switch field[0] {
case "rchar": case "rchar":
ret.ReadCount = mustParseInt32(strings.Trim(field[1], " \t")) ret.ReadCount = int32(t)
case "wchar": case "wchar":
ret.WriteCount = mustParseInt32(strings.Trim(field[1], " \t")) ret.WriteCount = int32(t)
case "read_bytes": case "read_bytes":
ret.ReadBytes = mustParseInt32(strings.Trim(field[1], " \t")) ret.ReadBytes = int32(t)
case "write_bytes": case "write_bytes":
ret.WriteBytes = mustParseInt32(strings.Trim(field[1], " \t")) ret.WriteBytes = int32(t)
} }
} }
@ -363,19 +381,43 @@ func (p *Process) fillFromStatm() (*MemoryInfoStat, *MemoryInfoExStat, error) {
} }
fields := strings.Split(string(contents), " ") fields := strings.Split(string(contents), " ")
vms := mustParseUint64(fields[0]) * PageSize vms, err := strconv.ParseUint(fields[0], 10, 64)
rss := mustParseUint64(fields[1]) * PageSize if err != nil {
return nil, nil, err
}
rss, err := strconv.ParseUint(fields[1], 10, 64)
if err != nil {
return nil, nil, err
}
memInfo := &MemoryInfoStat{ memInfo := &MemoryInfoStat{
RSS: rss, RSS: rss * PageSize,
VMS: vms, VMS: vms * PageSize,
}
shared, err := strconv.ParseUint(fields[2], 10, 64)
if err != nil {
return nil, nil, err
}
text, err := strconv.ParseUint(fields[3], 10, 64)
if err != nil {
return nil, nil, err
} }
lib, err := strconv.ParseUint(fields[4], 10, 64)
if err != nil {
return nil, nil, err
}
dirty, err := strconv.ParseUint(fields[5], 10, 64)
if err != nil {
return nil, nil, err
}
memInfoEx := &MemoryInfoExStat{ memInfoEx := &MemoryInfoExStat{
RSS: rss, RSS: rss * PageSize,
VMS: vms, VMS: vms * PageSize,
Shared: mustParseUint64(fields[2]) * PageSize, Shared: shared * PageSize,
Text: mustParseUint64(fields[3]) * PageSize, Text: text * PageSize,
Lib: mustParseUint64(fields[4]) * PageSize, Lib: lib * PageSize,
Dirty: mustParseUint64(fields[5]) * PageSize, Dirty: dirty * PageSize,
} }
return memInfo, memInfoEx, nil return memInfo, memInfoEx, nil
@ -458,12 +500,25 @@ func (p *Process) fillFromStat() (string, int32, *CPUTimesStat, int64, int32, er
termmap, err := getTerminalMap() termmap, err := getTerminalMap()
terminal := "" terminal := ""
if err == nil { if err == nil {
terminal = termmap[mustParseUint64(fields[6])] t, err := strconv.ParseUint(fields[6], 10, 64)
if err != nil {
return "", 0, nil, 0, 0, err
}
terminal = termmap[t]
} }
ppid := mustParseInt32(fields[3]) ppid, err := strconv.ParseInt(fields[3], 10, 32)
utime, _ := strconv.ParseFloat(fields[13], 64) if err != nil {
stime, _ := strconv.ParseFloat(fields[14], 64) return "", 0, nil, 0, 0, err
}
utime, err := strconv.ParseFloat(fields[13], 64)
if err != nil {
return "", 0, nil, 0, 0, err
}
stime, err := strconv.ParseFloat(fields[14], 64)
if err != nil {
return "", 0, nil, 0, 0, err
}
cpuTimes := &CPUTimesStat{ cpuTimes := &CPUTimesStat{
CPU: "cpu", CPU: "cpu",
@ -472,7 +527,12 @@ func (p *Process) fillFromStat() (string, int32, *CPUTimesStat, int64, int32, er
} }
bootTime, _ := BootTime() bootTime, _ := BootTime()
ctime := ((mustParseUint64(fields[21]) / uint64(ClockTicks)) + uint64(bootTime)) * 1000 t, err := strconv.ParseUint(fields[21], 10, 64)
if err != nil {
return "", 0, nil, 0, 0, err
}
ctime := ((t / uint64(ClockTicks)) + uint64(bootTime)) * 1000
createTime := int64(ctime) createTime := int64(ctime)
// p.Nice = mustParseInt32(fields[18]) // p.Nice = mustParseInt32(fields[18])
@ -480,7 +540,7 @@ func (p *Process) fillFromStat() (string, int32, *CPUTimesStat, int64, int32, er
snice, _ := syscall.Getpriority(PrioProcess, int(pid)) snice, _ := syscall.Getpriority(PrioProcess, int(pid))
nice := int32(snice) // FIXME: is this true? nice := int32(snice) // FIXME: is this true?
return terminal, ppid, cpuTimes, createTime, nice, nil return terminal, int32(ppid), cpuTimes, createTime, nice, nil
} }
func Pids() ([]int32, error) { func Pids() ([]int32, error) {

@ -4,8 +4,8 @@ package gopsutil
import ( import (
"os" "os"
"os/user"
"os/exec" "os/exec"
"os/user"
"strconv" "strconv"
"strings" "strings"
"syscall" "syscall"

Loading…
Cancel
Save