system diagnostics command
License: MIT Signed-off-by: Jeromy <jeromyj@gmail.com>
Jeromy committed
Oct 13, 2015 at 13:46 UTC
11104d401e4f697d60c403e8a7fdc4db883acdce
29 files changed
+3149
-1
Godeps/Godeps.json
+15
@@ -286,6 +286,21 @@
286
"ImportPath": "github.com/satori/go.uuid",
287
"Rev": "7c7f2020c4c9491594b85767967f4619c2fa75f9"
288
},
289
+ {
290
+ "ImportPath": "github.com/shirou/gopsutil/common",
291
+ "Comment": "1.0.0-167-g6a274c3",
292
+ "Rev": "6a274c3628382ab316340478300f5282b89f7778"
293
+ },
294
+ {
295
+ "ImportPath": "github.com/shirou/gopsutil/disk",
296
+ "Comment": "1.0.0-167-g6a274c3",
297
+ "Rev": "6a274c3628382ab316340478300f5282b89f7778"
298
+ },
299
+ {
300
+ "ImportPath": "github.com/shirou/gopsutil/mem",
301
+ "Comment": "1.0.0-167-g6a274c3",
302
+ "Rev": "6a274c3628382ab316340478300f5282b89f7778"
303
+ },
304
{
305
"ImportPath": "github.com/steakknife/hamming",
306
"Comment": "0.0.10",
Godeps/_workspace/src/github.com/shirou/gopsutil/common/common.go
new
+209
@@ -0,0 +1,209 @@
1
+//
2
+// gopsutil is a port of psutil(http://pythonhosted.org/psutil/).
3
+// This covers these architectures.
4
+// - linux (amd64, arm)
5
+// - freebsd (amd64)
6
+// - windows (amd64)
7
+package common
8
+
9
+import (
10
+ "bufio"
11
+ "errors"
12
+ "io/ioutil"
13
+ "net/url"
14
+ "os"
15
+ "os/exec"
16
+ "path"
17
+ "reflect"
18
+ "runtime"
19
+ "strconv"
20
+ "strings"
21
+)
22
+
23
+type Invoker interface {
24
+ Command(string, ...string) ([]byte, error)
25
+}
26
+
27
+type Invoke struct{}
28
+
29
+func (i Invoke) Command(name string, arg ...string) ([]byte, error) {
30
+ return exec.Command(name, arg...).Output()
31
+}
32
+
33
+type FakeInvoke struct {
34
+ CommandExpectedDir string // CommandExpectedDir specifies dir which includes expected outputs.
35
+ Suffix string // Suffix species expected file name suffix such as "fail"
36
+ Error error // If Error specfied, return the error.
37
+}
38
+
39
+// Command in FakeInvoke returns from expected file if exists.
40
+func (i FakeInvoke) Command(name string, arg ...string) ([]byte, error) {
41
+ if i.Error != nil {
42
+ return []byte{}, i.Error
43
+ }
44
+
45
+ arch := runtime.GOOS
46
+
47
+ fname := strings.Join(append([]string{name}, arg...), "")
48
+ fname = url.QueryEscape(fname)
49
+ var dir string
50
+ if i.CommandExpectedDir == "" {
51
+ dir = "expected"
52
+ } else {
53
+ dir = i.CommandExpectedDir
54
+ }
55
+ fpath := path.Join(dir, arch, fname)
56
+ if i.Suffix != "" {
57
+ fpath += "_" + i.Suffix
58
+ }
59
+ if PathExists(fpath) {
60
+ return ioutil.ReadFile(fpath)
61
+ } else {
62
+ return exec.Command(name, arg...).Output()
63
+ }
64
+}
65
+
66
+var NotImplementedError = errors.New("not implemented yet")
67
+
68
+// ReadLines reads contents from a file and splits them by new lines.
69
+// A convenience wrapper to ReadLinesOffsetN(filename, 0, -1).
70
+func ReadLines(filename string) ([]string, error) {
71
+ return ReadLinesOffsetN(filename, 0, -1)
72
+}
73
+
74
+// ReadLines reads contents from file and splits them by new line.
75
+// The offset tells at which line number to start.
76
+// The count determines the number of lines to read (starting from offset):
77
+// n >= 0: at most n lines
78
+// n < 0: whole file
79
+func ReadLinesOffsetN(filename string, offset uint, n int) ([]string, error) {
80
+ f, err := os.Open(filename)
81
+ if err != nil {
82
+ return []string{""}, err
83
+ }
84
+ defer f.Close()
85
+
86
+ var ret []string
87
+
88
+ r := bufio.NewReader(f)
89
+ for i := 0; i < n+int(offset) || n < 0; i++ {
90
+ line, err := r.ReadString('\n')
91
+ if err != nil {
92
+ break
93
+ }
94
+ if i < int(offset) {
95
+ continue
96
+ }
97
+ ret = append(ret, strings.Trim(line, "\n"))
98
+ }
99
+
100
+ return ret, nil
101
+}
102
+
103
+func IntToString(orig []int8) string {
104
+ ret := make([]byte, len(orig))
105
+ size := -1
106
+ for i, o := range orig {
107
+ if o == 0 {
108
+ size = i
109
+ break
110
+ }
111
+ ret[i] = byte(o)
112
+ }
113
+ if size == -1 {
114
+ size = len(orig)
115
+ }
116
+
117
+ return string(ret[0:size])
118
+}
119
+
120
+func ByteToString(orig []byte) string {
121
+ n := -1
122
+ l := -1
123
+ for i, b := range orig {
124
+ // skip left side null
125
+ if l == -1 && b == 0 {
126
+ continue
127
+ }
128
+ if l == -1 {
129
+ l = i
130
+ }
131
+
132
+ if b == 0 {
133
+ break
134
+ }
135
+ n = i + 1
136
+ }
137
+ if n == -1 {
138
+ return string(orig)
139
+ }
140
+ return string(orig[l:n])
141
+}
142
+
143
+// Parse to int32 without error
144
+func mustParseInt32(val string) int32 {
145
+ vv, _ := strconv.ParseInt(val, 10, 32)
146
+ return int32(vv)
147
+}
148
+
149
+// Parse to uint64 without error
150
+func mustParseUint64(val string) uint64 {
151
+ vv, _ := strconv.ParseInt(val, 10, 64)
152
+ return uint64(vv)
153
+}
154
+
155
+// Parse to Float64 without error
156
+func mustParseFloat64(val string) float64 {
157
+ vv, _ := strconv.ParseFloat(val, 64)
158
+ return vv
159
+}
160
+
161
+// StringsHas checks the target string slice containes src or not
162
+func StringsHas(target []string, src string) bool {
163
+ for _, t := range target {
164
+ if strings.TrimSpace(t) == src {
165
+ return true
166
+ }
167
+ }
168
+ return false
169
+}
170
+
171
+// StringsContains checks the src in any string of the target string slice
172
+func StringsContains(target []string, src string) bool {
173
+ for _, t := range target {
174
+ if strings.Contains(t, src) {
175
+ return true
176
+ }
177
+ }
178
+ return false
179
+}
180
+
181
+// get struct attributes.
182
+// This method is used only for debugging platform dependent code.
183
+func attributes(m interface{}) map[string]reflect.Type {
184
+ typ := reflect.TypeOf(m)
185
+ if typ.Kind() == reflect.Ptr {
186
+ typ = typ.Elem()
187
+ }
188
+
189
+ attrs := make(map[string]reflect.Type)
190
+ if typ.Kind() != reflect.Struct {
191
+ return nil
192
+ }
193
+
194
+ for i := 0; i < typ.NumField(); i++ {
195
+ p := typ.Field(i)
196
+ if !p.Anonymous {
197
+ attrs[p.Name] = p.Type
198
+ }
199
+ }
200
+
201
+ return attrs
202
+}
203
+
204
+func PathExists(filename string) bool {
205
+ if _, err := os.Stat(filename); err == nil {
206
+ return true
207
+ }
208
+ return false
209
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/common/common_darwin.go
new
+60
@@ -0,0 +1,60 @@
1
+// +build darwin
2
+
3
+package common
4
+
5
+import (
6
+ "os/exec"
7
+ "strings"
8
+ "syscall"
9
+ "unsafe"
10
+)
11
+
12
+func DoSysctrl(mib string) ([]string, error) {
13
+ out, err := exec.Command("/usr/sbin/sysctl", "-n", mib).Output()
14
+ if err != nil {
15
+ return []string{}, err
16
+ }
17
+ v := strings.Replace(string(out), "{ ", "", 1)
18
+ v = strings.Replace(string(v), " }", "", 1)
19
+ values := strings.Fields(string(v))
20
+
21
+ return values, nil
22
+}
23
+
24
+func CallSyscall(mib []int32) ([]byte, uint64, error) {
25
+ miblen := uint64(len(mib))
26
+
27
+ // get required buffer size
28
+ length := uint64(0)
29
+ _, _, err := syscall.Syscall6(
30
+ syscall.SYS___SYSCTL,
31
+ uintptr(unsafe.Pointer(&mib[0])),
32
+ uintptr(miblen),
33
+ 0,
34
+ uintptr(unsafe.Pointer(&length)),
35
+ 0,
36
+ 0)
37
+ if err != 0 {
38
+ var b []byte
39
+ return b, length, err
40
+ }
41
+ if length == 0 {
42
+ var b []byte
43
+ return b, length, err
44
+ }
45
+ // get proc info itself
46
+ buf := make([]byte, length)
47
+ _, _, err = syscall.Syscall6(
48
+ syscall.SYS___SYSCTL,
49
+ uintptr(unsafe.Pointer(&mib[0])),
50
+ uintptr(miblen),
51
+ uintptr(unsafe.Pointer(&buf[0])),
52
+ uintptr(unsafe.Pointer(&length)),
53
+ 0,
54
+ 0)
55
+ if err != 0 {
56
+ return buf, length, err
57
+ }
58
+
59
+ return buf, length, nil
60
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/common/common_freebsd.go
new
+60
@@ -0,0 +1,60 @@
1
+// +build freebsd
2
+
3
+package common
4
+
5
+import (
6
+ "syscall"
7
+ "os/exec"
8
+ "strings"
9
+ "unsafe"
10
+)
11
+
12
+func DoSysctrl(mib string) ([]string, error) {
13
+ out, err := exec.Command("/sbin/sysctl", "-n", mib).Output()
14
+ if err != nil {
15
+ return []string{}, err
16
+ }
17
+ v := strings.Replace(string(out), "{ ", "", 1)
18
+ v = strings.Replace(string(v), " }", "", 1)
19
+ values := strings.Fields(string(v))
20
+
21
+ return values, nil
22
+}
23
+
24
+func CallSyscall(mib []int32) ([]byte, uint64, error) {
25
+ miblen := uint64(len(mib))
26
+
27
+ // get required buffer size
28
+ length := uint64(0)
29
+ _, _, err := syscall.Syscall6(
30
+ syscall.SYS___SYSCTL,
31
+ uintptr(unsafe.Pointer(&mib[0])),
32
+ uintptr(miblen),
33
+ 0,
34
+ uintptr(unsafe.Pointer(&length)),
35
+ 0,
36
+ 0)
37
+ if err != 0 {
38
+ var b []byte
39
+ return b, length, err
40
+ }
41
+ if length == 0 {
42
+ var b []byte
43
+ return b, length, err
44
+ }
45
+ // get proc info itself
46
+ buf := make([]byte, length)
47
+ _, _, err = syscall.Syscall6(
48
+ syscall.SYS___SYSCTL,
49
+ uintptr(unsafe.Pointer(&mib[0])),
50
+ uintptr(miblen),
51
+ uintptr(unsafe.Pointer(&buf[0])),
52
+ uintptr(unsafe.Pointer(&length)),
53
+ 0,
54
+ 0)
55
+ if err != 0 {
56
+ return buf, length, err
57
+ }
58
+
59
+ return buf, length, nil
60
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/common/common_linux.go
new
+3
@@ -0,0 +1,3 @@
1
+// +build linux
2
+
3
+package common
Godeps/_workspace/src/github.com/shirou/gopsutil/common/common_test.go
new
+90
@@ -0,0 +1,90 @@
1
+package common
2
+
3
+import (
4
+ "fmt"
5
+ "strings"
6
+ "testing"
7
+)
8
+
9
+func TestReadlines(t *testing.T) {
10
+ ret, err := ReadLines("common_test.go")
11
+ if err != nil {
12
+ t.Error(err)
13
+ }
14
+ if !strings.Contains(ret[0], "package common") {
15
+ t.Error("could not read correctly")
16
+ }
17
+}
18
+
19
+func TestReadLinesOffsetN(t *testing.T) {
20
+ ret, err := ReadLinesOffsetN("common_test.go", 2, 1)
21
+ if err != nil {
22
+ t.Error(err)
23
+ }
24
+ fmt.Println(ret[0])
25
+ if !strings.Contains(ret[0], `import (`) {
26
+ t.Error("could not read correctly")
27
+ }
28
+}
29
+
30
+func TestIntToString(t *testing.T) {
31
+ src := []int8{65, 66, 67}
32
+ dst := IntToString(src)
33
+ if dst != "ABC" {
34
+ t.Error("could not convert")
35
+ }
36
+}
37
+func TestByteToString(t *testing.T) {
38
+ src := []byte{65, 66, 67}
39
+ dst := ByteToString(src)
40
+ if dst != "ABC" {
41
+ t.Error("could not convert")
42
+ }
43
+
44
+ src = []byte{0, 65, 66, 67}
45
+ dst = ByteToString(src)
46
+ if dst != "ABC" {
47
+ t.Error("could not convert")
48
+ }
49
+}
50
+
51
+func TestmustParseInt32(t *testing.T) {
52
+ ret := mustParseInt32("11111")
53
+ if ret != int32(11111) {
54
+ t.Error("could not parse")
55
+ }
56
+}
57
+func TestmustParseUint64(t *testing.T) {
58
+ ret := mustParseUint64("11111")
59
+ if ret != uint64(11111) {
60
+ t.Error("could not parse")
61
+ }
62
+}
63
+func TestmustParseFloat64(t *testing.T) {
64
+ ret := mustParseFloat64("11111.11")
65
+ if ret != float64(11111.11) {
66
+ t.Error("could not parse")
67
+ }
68
+ ret = mustParseFloat64("11111")
69
+ if ret != float64(11111) {
70
+ t.Error("could not parse")
71
+ }
72
+}
73
+func TestStringsContains(t *testing.T) {
74
+ target, err := ReadLines("common_test.go")
75
+ if err != nil {
76
+ t.Error(err)
77
+ }
78
+ if !StringsContains(target, "func TestStringsContains(t *testing.T) {") {
79
+ t.Error("cloud not test correctly")
80
+ }
81
+}
82
+
83
+func TestPathExists(t *testing.T) {
84
+ if !PathExists("common_test.go") {
85
+ t.Error("exists but return not exists")
86
+ }
87
+ if PathExists("should_not_exists.go") {
88
+ t.Error("not exists but return exists")
89
+ }
90
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/common/common_unix.go
new
+40
@@ -0,0 +1,40 @@
1
+// +build linux freebsd darwin
2
+
3
+package common
4
+
5
+import (
6
+ "os/exec"
7
+ "strconv"
8
+ "strings"
9
+)
10
+
11
+func CallLsof(invoke Invoker, pid int32, args ...string) ([]string, error) {
12
+ var cmd []string
13
+ if pid == 0 { // will get from all processes.
14
+ cmd = []string{"-a", "-n", "-P"}
15
+ } else {
16
+ cmd = []string{"-a", "-n", "-P", "-p", strconv.Itoa(int(pid))}
17
+ }
18
+ cmd = append(cmd, args...)
19
+ lsof, err := exec.LookPath("lsof")
20
+ if err != nil {
21
+ return []string{}, err
22
+ }
23
+ out, err := invoke.Command(lsof, cmd...)
24
+ if err != nil {
25
+ // if no pid found, lsof returnes code 1.
26
+ if err.Error() == "exit status 1" && len(out) == 0 {
27
+ return []string{}, nil
28
+ }
29
+ }
30
+ lines := strings.Split(string(out), "\n")
31
+
32
+ var ret []string
33
+ for _, l := range lines[1:] {
34
+ if len(l) == 0 {
35
+ continue
36
+ }
37
+ ret = append(ret, l)
38
+ }
39
+ return ret, nil
40
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/common/common_windows.go
new
+110
@@ -0,0 +1,110 @@
1
+// +build windows
2
+
3
+package common
4
+
5
+import (
6
+ "syscall"
7
+ "unsafe"
8
+)
9
+
10
+// for double values
11
+type PDH_FMT_COUNTERVALUE_DOUBLE struct {
12
+ CStatus uint32
13
+ DoubleValue float64
14
+}
15
+
16
+// for 64 bit integer values
17
+type PDH_FMT_COUNTERVALUE_LARGE struct {
18
+ CStatus uint32
19
+ LargeValue int64
20
+}
21
+
22
+// for long values
23
+type PDH_FMT_COUNTERVALUE_LONG struct {
24
+ CStatus uint32
25
+ LongValue int32
26
+ padding [4]byte
27
+}
28
+
29
+// windows system const
30
+const (
31
+ ERROR_SUCCESS = 0
32
+ ERROR_FILE_NOT_FOUND = 2
33
+ DRIVE_REMOVABLE = 2
34
+ DRIVE_FIXED = 3
35
+ HKEY_LOCAL_MACHINE = 0x80000002
36
+ RRF_RT_REG_SZ = 0x00000002
37
+ RRF_RT_REG_DWORD = 0x00000010
38
+ PDH_FMT_LONG = 0x00000100
39
+ PDH_FMT_DOUBLE = 0x00000200
40
+ PDH_FMT_LARGE = 0x00000400
41
+ PDH_INVALID_DATA = 0xc0000bc6
42
+ PDH_INVALID_HANDLE = 0xC0000bbc
43
+ PDH_NO_DATA = 0x800007d5
44
+)
45
+
46
+var (
47
+ Modkernel32 = syscall.NewLazyDLL("kernel32.dll")
48
+ ModNt = syscall.NewLazyDLL("ntdll.dll")
49
+ ModPdh = syscall.NewLazyDLL("pdh.dll")
50
+
51
+ ProcGetSystemTimes = Modkernel32.NewProc("GetSystemTimes")
52
+ ProcNtQuerySystemInformation = ModNt.NewProc("NtQuerySystemInformation")
53
+ PdhOpenQuery = ModPdh.NewProc("PdhOpenQuery")
54
+ PdhAddCounter = ModPdh.NewProc("PdhAddCounterW")
55
+ PdhCollectQueryData = ModPdh.NewProc("PdhCollectQueryData")
56
+ PdhGetFormattedCounterValue = ModPdh.NewProc("PdhGetFormattedCounterValue")
57
+ PdhCloseQuery = ModPdh.NewProc("PdhCloseQuery")
58
+)
59
+
60
+type FILETIME struct {
61
+ DwLowDateTime uint32
62
+ DwHighDateTime uint32
63
+}
64
+
65
+// borrowed from net/interface_windows.go
66
+func BytePtrToString(p *uint8) string {
67
+ a := (*[10000]uint8)(unsafe.Pointer(p))
68
+ i := 0
69
+ for a[i] != 0 {
70
+ i++
71
+ }
72
+ return string(a[:i])
73
+}
74
+
75
+// CounterInfo
76
+// copied from https://github.com/mackerelio/mackerel-agent/
77
+type CounterInfo struct {
78
+ PostName string
79
+ CounterName string
80
+ Counter syscall.Handle
81
+}
82
+
83
+// CreateQuery XXX
84
+// copied from https://github.com/mackerelio/mackerel-agent/
85
+func CreateQuery() (syscall.Handle, error) {
86
+ var query syscall.Handle
87
+ r, _, err := PdhOpenQuery.Call(0, 0, uintptr(unsafe.Pointer(&query)))
88
+ if r != 0 {
89
+ return 0, err
90
+ }
91
+ return query, nil
92
+}
93
+
94
+// CreateCounter XXX
95
+func CreateCounter(query syscall.Handle, pname, cname string) (*CounterInfo, error) {
96
+ var counter syscall.Handle
97
+ r, _, err := PdhAddCounter.Call(
98
+ uintptr(query),
99
+ uintptr(unsafe.Pointer(syscall.StringToUTF16Ptr(cname))),
100
+ 0,
101
+ uintptr(unsafe.Pointer(&counter)))
102
+ if r != 0 {
103
+ return nil, err
104
+ }
105
+ return &CounterInfo{
106
+ PostName: pname,
107
+ CounterName: cname,
108
+ Counter: counter,
109
+ }, nil
110
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/disk/binary.go
new
+634
@@ -0,0 +1,634 @@
1
+// Copyright 2009 The Go Authors. All rights reserved.
2
+// Use of this source code is governed by a BSD-style
3
+// license that can be found in the LICENSE file.
4
+
5
+// Package binary implements simple translation between numbers and byte
6
+// sequences and encoding and decoding of varints.
7
+//
8
+// Numbers are translated by reading and writing fixed-size values.
9
+// A fixed-size value is either a fixed-size arithmetic
10
+// type (int8, uint8, int16, float32, complex64, ...)
11
+// or an array or struct containing only fixed-size values.
12
+//
13
+// The varint functions encode and decode single integer values using
14
+// a variable-length encoding; smaller values require fewer bytes.
15
+// For a specification, see
16
+// http://code.google.com/apis/protocolbuffers/docs/encoding.html.
17
+//
18
+// This package favors simplicity over efficiency. Clients that require
19
+// high-performance serialization, especially for large data structures,
20
+// should look at more advanced solutions such as the encoding/gob
21
+// package or protocol buffers.
22
+package disk
23
+
24
+import (
25
+ "errors"
26
+ "io"
27
+ "math"
28
+ "reflect"
29
+)
30
+
31
+// A ByteOrder specifies how to convert byte sequences into
32
+// 16-, 32-, or 64-bit unsigned integers.
33
+type ByteOrder interface {
34
+ Uint16([]byte) uint16
35
+ Uint32([]byte) uint32
36
+ Uint64([]byte) uint64
37
+ PutUint16([]byte, uint16)
38
+ PutUint32([]byte, uint32)
39
+ PutUint64([]byte, uint64)
40
+ String() string
41
+}
42
+
43
+// LittleEndian is the little-endian implementation of ByteOrder.
44
+var LittleEndian littleEndian
45
+
46
+// BigEndian is the big-endian implementation of ByteOrder.
47
+var BigEndian bigEndian
48
+
49
+type littleEndian struct{}
50
+
51
+func (littleEndian) Uint16(b []byte) uint16 { return uint16(b[0]) | uint16(b[1])<<8 }
52
+
53
+func (littleEndian) PutUint16(b []byte, v uint16) {
54
+ b[0] = byte(v)
55
+ b[1] = byte(v >> 8)
56
+}
57
+
58
+func (littleEndian) Uint32(b []byte) uint32 {
59
+ return uint32(b[0]) | uint32(b[1])<<8 | uint32(b[2])<<16 | uint32(b[3])<<24
60
+}
61
+
62
+func (littleEndian) PutUint32(b []byte, v uint32) {
63
+ b[0] = byte(v)
64
+ b[1] = byte(v >> 8)
65
+ b[2] = byte(v >> 16)
66
+ b[3] = byte(v >> 24)
67
+}
68
+
69
+func (littleEndian) Uint64(b []byte) uint64 {
70
+ return uint64(b[0]) | uint64(b[1])<<8 | uint64(b[2])<<16 | uint64(b[3])<<24 |
71
+ uint64(b[4])<<32 | uint64(b[5])<<40 | uint64(b[6])<<48 | uint64(b[7])<<56
72
+}
73
+
74
+func (littleEndian) PutUint64(b []byte, v uint64) {
75
+ b[0] = byte(v)
76
+ b[1] = byte(v >> 8)
77
+ b[2] = byte(v >> 16)
78
+ b[3] = byte(v >> 24)
79
+ b[4] = byte(v >> 32)
80
+ b[5] = byte(v >> 40)
81
+ b[6] = byte(v >> 48)
82
+ b[7] = byte(v >> 56)
83
+}
84
+
85
+func (littleEndian) String() string { return "LittleEndian" }
86
+
87
+func (littleEndian) GoString() string { return "binary.LittleEndian" }
88
+
89
+type bigEndian struct{}
90
+
91
+func (bigEndian) Uint16(b []byte) uint16 { return uint16(b[1]) | uint16(b[0])<<8 }
92
+
93
+func (bigEndian) PutUint16(b []byte, v uint16) {
94
+ b[0] = byte(v >> 8)
95
+ b[1] = byte(v)
96
+}
97
+
98
+func (bigEndian) Uint32(b []byte) uint32 {
99
+ return uint32(b[3]) | uint32(b[2])<<8 | uint32(b[1])<<16 | uint32(b[0])<<24
100
+}
101
+
102
+func (bigEndian) PutUint32(b []byte, v uint32) {
103
+ b[0] = byte(v >> 24)
104
+ b[1] = byte(v >> 16)
105
+ b[2] = byte(v >> 8)
106
+ b[3] = byte(v)
107
+}
108
+
109
+func (bigEndian) Uint64(b []byte) uint64 {
110
+ return uint64(b[7]) | uint64(b[6])<<8 | uint64(b[5])<<16 | uint64(b[4])<<24 |
111
+ uint64(b[3])<<32 | uint64(b[2])<<40 | uint64(b[1])<<48 | uint64(b[0])<<56
112
+}
113
+
114
+func (bigEndian) PutUint64(b []byte, v uint64) {
115
+ b[0] = byte(v >> 56)
116
+ b[1] = byte(v >> 48)
117
+ b[2] = byte(v >> 40)
118
+ b[3] = byte(v >> 32)
119
+ b[4] = byte(v >> 24)
120
+ b[5] = byte(v >> 16)
121
+ b[6] = byte(v >> 8)
122
+ b[7] = byte(v)
123
+}
124
+
125
+func (bigEndian) String() string { return "BigEndian" }
126
+
127
+func (bigEndian) GoString() string { return "binary.BigEndian" }
128
+
129
+// Read reads structured binary data from r into data.
130
+// Data must be a pointer to a fixed-size value or a slice
131
+// of fixed-size values.
132
+// Bytes read from r are decoded using the specified byte order
133
+// and written to successive fields of the data.
134
+// When reading into structs, the field data for fields with
135
+// blank (_) field names is skipped; i.e., blank field names
136
+// may be used for padding.
137
+// When reading into a struct, all non-blank fields must be exported.
138
+func Read(r io.Reader, order ByteOrder, data interface{}) error {
139
+ // Fast path for basic types and slices.
140
+ if n := intDataSize(data); n != 0 {
141
+ var b [8]byte
142
+ var bs []byte
143
+ if n > len(b) {
144
+ bs = make([]byte, n)
145
+ } else {
146
+ bs = b[:n]
147
+ }
148
+ if _, err := io.ReadFull(r, bs); err != nil {
149
+ return err
150
+ }
151
+ switch data := data.(type) {
152
+ case *int8:
153
+ *data = int8(b[0])
154
+ case *uint8:
155
+ *data = b[0]
156
+ case *int16:
157
+ *data = int16(order.Uint16(bs))
158
+ case *uint16:
159
+ *data = order.Uint16(bs)
160
+ case *int32:
161
+ *data = int32(order.Uint32(bs))
162
+ case *uint32:
163
+ *data = order.Uint32(bs)
164
+ case *int64:
165
+ *data = int64(order.Uint64(bs))
166
+ case *uint64:
167
+ *data = order.Uint64(bs)
168
+ case []int8:
169
+ for i, x := range bs { // Easier to loop over the input for 8-bit values.
170
+ data[i] = int8(x)
171
+ }
172
+ case []uint8:
173
+ copy(data, bs)
174
+ case []int16:
175
+ for i := range data {
176
+ data[i] = int16(order.Uint16(bs[2*i:]))
177
+ }
178
+ case []uint16:
179
+ for i := range data {
180
+ data[i] = order.Uint16(bs[2*i:])
181
+ }
182
+ case []int32:
183
+ for i := range data {
184
+ data[i] = int32(order.Uint32(bs[4*i:]))
185
+ }
186
+ case []uint32:
187
+ for i := range data {
188
+ data[i] = order.Uint32(bs[4*i:])
189
+ }
190
+ case []int64:
191
+ for i := range data {
192
+ data[i] = int64(order.Uint64(bs[8*i:]))
193
+ }
194
+ case []uint64:
195
+ for i := range data {
196
+ data[i] = order.Uint64(bs[8*i:])
197
+ }
198
+ }
199
+ return nil
200
+ }
201
+
202
+ // Fallback to reflect-based decoding.
203
+ v := reflect.ValueOf(data)
204
+ size := -1
205
+ switch v.Kind() {
206
+ case reflect.Ptr:
207
+ v = v.Elem()
208
+ size = dataSize(v)
209
+ case reflect.Slice:
210
+ size = dataSize(v)
211
+ }
212
+ if size < 0 {
213
+ return errors.New("binary.Read: invalid type " + reflect.TypeOf(data).String())
214
+ }
215
+ d := &decoder{order: order, buf: make([]byte, size)}
216
+ if _, err := io.ReadFull(r, d.buf); err != nil {
217
+ return err
218
+ }
219
+ d.value(v)
220
+ return nil
221
+}
222
+
223
+// Write writes the binary representation of data into w.
224
+// Data must be a fixed-size value or a slice of fixed-size
225
+// values, or a pointer to such data.
226
+// Bytes written to w are encoded using the specified byte order
227
+// and read from successive fields of the data.
228
+// When writing structs, zero values are written for fields
229
+// with blank (_) field names.
230
+func Write(w io.Writer, order ByteOrder, data interface{}) error {
231
+ // Fast path for basic types and slices.
232
+ if n := intDataSize(data); n != 0 {
233
+ var b [8]byte
234
+ var bs []byte
235
+ if n > len(b) {
236
+ bs = make([]byte, n)
237
+ } else {
238
+ bs = b[:n]
239
+ }
240
+ switch v := data.(type) {
241
+ case *int8:
242
+ bs = b[:1]
243
+ b[0] = byte(*v)
244
+ case int8:
245
+ bs = b[:1]
246
+ b[0] = byte(v)
247
+ case []int8:
248
+ for i, x := range v {
249
+ bs[i] = byte(x)
250
+ }
251
+ case *uint8:
252
+ bs = b[:1]
253
+ b[0] = *v
254
+ case uint8:
255
+ bs = b[:1]
256
+ b[0] = byte(v)
257
+ case []uint8:
258
+ bs = v
259
+ case *int16:
260
+ bs = b[:2]
261
+ order.PutUint16(bs, uint16(*v))
262
+ case int16:
263
+ bs = b[:2]
264
+ order.PutUint16(bs, uint16(v))
265
+ case []int16:
266
+ for i, x := range v {
267
+ order.PutUint16(bs[2*i:], uint16(x))
268
+ }
269
+ case *uint16:
270
+ bs = b[:2]
271
+ order.PutUint16(bs, *v)
272
+ case uint16:
273
+ bs = b[:2]
274
+ order.PutUint16(bs, v)
275
+ case []uint16:
276
+ for i, x := range v {
277
+ order.PutUint16(bs[2*i:], x)
278
+ }
279
+ case *int32:
280
+ bs = b[:4]
281
+ order.PutUint32(bs, uint32(*v))
282
+ case int32:
283
+ bs = b[:4]
284
+ order.PutUint32(bs, uint32(v))
285
+ case []int32:
286
+ for i, x := range v {
287
+ order.PutUint32(bs[4*i:], uint32(x))
288
+ }
289
+ case *uint32:
290
+ bs = b[:4]
291
+ order.PutUint32(bs, *v)
292
+ case uint32:
293
+ bs = b[:4]
294
+ order.PutUint32(bs, v)
295
+ case []uint32:
296
+ for i, x := range v {
297
+ order.PutUint32(bs[4*i:], x)
298
+ }
299
+ case *int64:
300
+ bs = b[:8]
301
+ order.PutUint64(bs, uint64(*v))
302
+ case int64:
303
+ bs = b[:8]
304
+ order.PutUint64(bs, uint64(v))
305
+ case []int64:
306
+ for i, x := range v {
307
+ order.PutUint64(bs[8*i:], uint64(x))
308
+ }
309
+ case *uint64:
310
+ bs = b[:8]
311
+ order.PutUint64(bs, *v)
312
+ case uint64:
313
+ bs = b[:8]
314
+ order.PutUint64(bs, v)
315
+ case []uint64:
316
+ for i, x := range v {
317
+ order.PutUint64(bs[8*i:], x)
318
+ }
319
+ }
320
+ _, err := w.Write(bs)
321
+ return err
322
+ }
323
+
324
+ // Fallback to reflect-based encoding.
325
+ v := reflect.Indirect(reflect.ValueOf(data))
326
+ size := dataSize(v)
327
+ if size < 0 {
328
+ return errors.New("binary.Write: invalid type " + reflect.TypeOf(data).String())
329
+ }
330
+ buf := make([]byte, size)
331
+ e := &encoder{order: order, buf: buf}
332
+ e.value(v)
333
+ _, err := w.Write(buf)
334
+ return err
335
+}
336
+
337
+// Size returns how many bytes Write would generate to encode the value v, which
338
+// must be a fixed-size value or a slice of fixed-size values, or a pointer to such data.
339
+// If v is neither of these, Size returns -1.
340
+func Size(v interface{}) int {
341
+ return dataSize(reflect.Indirect(reflect.ValueOf(v)))
342
+}
343
+
344
+// dataSize returns the number of bytes the actual data represented by v occupies in memory.
345
+// For compound structures, it sums the sizes of the elements. Thus, for instance, for a slice
346
+// it returns the length of the slice times the element size and does not count the memory
347
+// occupied by the header. If the type of v is not acceptable, dataSize returns -1.
348
+func dataSize(v reflect.Value) int {
349
+ if v.Kind() == reflect.Slice {
350
+ if s := sizeof(v.Type().Elem()); s >= 0 {
351
+ return s * v.Len()
352
+ }
353
+ return -1
354
+ }
355
+ return sizeof(v.Type())
356
+}
357
+
358
+// sizeof returns the size >= 0 of variables for the given type or -1 if the type is not acceptable.
359
+func sizeof(t reflect.Type) int {
360
+ switch t.Kind() {
361
+ case reflect.Array:
362
+ if s := sizeof(t.Elem()); s >= 0 {
363
+ return s * t.Len()
364
+ }
365
+
366
+ case reflect.Struct:
367
+ sum := 0
368
+ for i, n := 0, t.NumField(); i < n; i++ {
369
+ s := sizeof(t.Field(i).Type)
370
+ if s < 0 {
371
+ return -1
372
+ }
373
+ sum += s
374
+ }
375
+ return sum
376
+
377
+ case reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64,
378
+ reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64,
379
+ reflect.Float32, reflect.Float64, reflect.Complex64, reflect.Complex128, reflect.Ptr:
380
+ return int(t.Size())
381
+ }
382
+
383
+ return -1
384
+}
385
+
386
+type coder struct {
387
+ order ByteOrder
388
+ buf []byte
389
+}
390
+
391
+type decoder coder
392
+type encoder coder
393
+
394
+func (d *decoder) uint8() uint8 {
395
+ x := d.buf[0]
396
+ d.buf = d.buf[1:]
397
+ return x
398
+}
399
+
400
+func (e *encoder) uint8(x uint8) {
401
+ e.buf[0] = x
402
+ e.buf = e.buf[1:]
403
+}
404
+
405
+func (d *decoder) uint16() uint16 {
406
+ x := d.order.Uint16(d.buf[0:2])
407
+ d.buf = d.buf[2:]
408
+ return x
409
+}
410
+
411
+func (e *encoder) uint16(x uint16) {
412
+ e.order.PutUint16(e.buf[0:2], x)
413
+ e.buf = e.buf[2:]
414
+}
415
+
416
+func (d *decoder) uint32() uint32 {
417
+ x := d.order.Uint32(d.buf[0:4])
418
+ d.buf = d.buf[4:]
419
+ return x
420
+}
421
+
422
+func (e *encoder) uint32(x uint32) {
423
+ e.order.PutUint32(e.buf[0:4], x)
424
+ e.buf = e.buf[4:]
425
+}
426
+
427
+func (d *decoder) uint64() uint64 {
428
+ x := d.order.Uint64(d.buf[0:8])
429
+ d.buf = d.buf[8:]
430
+ return x
431
+}
432
+
433
+func (e *encoder) uint64(x uint64) {
434
+ e.order.PutUint64(e.buf[0:8], x)
435
+ e.buf = e.buf[8:]
436
+}
437
+
438
+func (d *decoder) int8() int8 { return int8(d.uint8()) }
439
+
440
+func (e *encoder) int8(x int8) { e.uint8(uint8(x)) }
441
+
442
+func (d *decoder) int16() int16 { return int16(d.uint16()) }
443
+
444
+func (e *encoder) int16(x int16) { e.uint16(uint16(x)) }
445
+
446
+func (d *decoder) int32() int32 { return int32(d.uint32()) }
447
+
448
+func (e *encoder) int32(x int32) { e.uint32(uint32(x)) }
449
+
450
+func (d *decoder) int64() int64 { return int64(d.uint64()) }
451
+
452
+func (e *encoder) int64(x int64) { e.uint64(uint64(x)) }
453
+
454
+func (d *decoder) value(v reflect.Value) {
455
+ switch v.Kind() {
456
+ case reflect.Array:
457
+ l := v.Len()
458
+ for i := 0; i < l; i++ {
459
+ d.value(v.Index(i))
460
+ }
461
+
462
+ case reflect.Struct:
463
+ t := v.Type()
464
+ l := v.NumField()
465
+ for i := 0; i < l; i++ {
466
+ // Note: Calling v.CanSet() below is an optimization.
467
+ // It would be sufficient to check the field name,
468
+ // but creating the StructField info for each field is
469
+ // costly (run "go test -bench=ReadStruct" and compare
470
+ // results when making changes to this code).
471
+ if v := v.Field(i); v.CanSet() || t.Field(i).Name != "_" {
472
+ d.value(v)
473
+ } else {
474
+ d.skip(v)
475
+ }
476
+ }
477
+
478
+ case reflect.Slice:
479
+ l := v.Len()
480
+ for i := 0; i < l; i++ {
481
+ d.value(v.Index(i))
482
+ }
483
+
484
+ case reflect.Int8:
485
+ v.SetInt(int64(d.int8()))
486
+ case reflect.Int16:
487
+ v.SetInt(int64(d.int16()))
488
+ case reflect.Int32:
489
+ v.SetInt(int64(d.int32()))
490
+ case reflect.Int64:
491
+ v.SetInt(d.int64())
492
+
493
+ case reflect.Uint8:
494
+ v.SetUint(uint64(d.uint8()))
495
+ case reflect.Uint16:
496
+ v.SetUint(uint64(d.uint16()))
497
+ case reflect.Uint32:
498
+ v.SetUint(uint64(d.uint32()))
499
+ case reflect.Uint64:
500
+ v.SetUint(d.uint64())
501
+
502
+ case reflect.Float32:
503
+ v.SetFloat(float64(math.Float32frombits(d.uint32())))
504
+ case reflect.Float64:
505
+ v.SetFloat(math.Float64frombits(d.uint64()))
506
+
507
+ case reflect.Complex64:
508
+ v.SetComplex(complex(
509
+ float64(math.Float32frombits(d.uint32())),
510
+ float64(math.Float32frombits(d.uint32())),
511
+ ))
512
+ case reflect.Complex128:
513
+ v.SetComplex(complex(
514
+ math.Float64frombits(d.uint64()),
515
+ math.Float64frombits(d.uint64()),
516
+ ))
517
+ }
518
+}
519
+
520
+func (e *encoder) value(v reflect.Value) {
521
+ switch v.Kind() {
522
+ case reflect.Array:
523
+ l := v.Len()
524
+ for i := 0; i < l; i++ {
525
+ e.value(v.Index(i))
526
+ }
527
+
528
+ case reflect.Struct:
529
+ t := v.Type()
530
+ l := v.NumField()
531
+ for i := 0; i < l; i++ {
532
+ // see comment for corresponding code in decoder.value()
533
+ if v := v.Field(i); v.CanSet() || t.Field(i).Name != "_" {
534
+ e.value(v)
535
+ } else {
536
+ e.skip(v)
537
+ }
538
+ }
539
+
540
+ case reflect.Slice:
541
+ l := v.Len()
542
+ for i := 0; i < l; i++ {
543
+ e.value(v.Index(i))
544
+ }
545
+
546
+ case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
547
+ switch v.Type().Kind() {
548
+ case reflect.Int8:
549
+ e.int8(int8(v.Int()))
550
+ case reflect.Int16:
551
+ e.int16(int16(v.Int()))
552
+ case reflect.Int32:
553
+ e.int32(int32(v.Int()))
554
+ case reflect.Int64:
555
+ e.int64(v.Int())
556
+ }
557
+
558
+ case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
559
+ switch v.Type().Kind() {
560
+ case reflect.Uint8:
561
+ e.uint8(uint8(v.Uint()))
562
+ case reflect.Uint16:
563
+ e.uint16(uint16(v.Uint()))
564
+ case reflect.Uint32:
565
+ e.uint32(uint32(v.Uint()))
566
+ case reflect.Uint64:
567
+ e.uint64(v.Uint())
568
+ }
569
+
570
+ case reflect.Float32, reflect.Float64:
571
+ switch v.Type().Kind() {
572
+ case reflect.Float32:
573
+ e.uint32(math.Float32bits(float32(v.Float())))
574
+ case reflect.Float64:
575
+ e.uint64(math.Float64bits(v.Float()))
576
+ }
577
+
578
+ case reflect.Complex64, reflect.Complex128:
579
+ switch v.Type().Kind() {
580
+ case reflect.Complex64:
581
+ x := v.Complex()
582
+ e.uint32(math.Float32bits(float32(real(x))))
583
+ e.uint32(math.Float32bits(float32(imag(x))))
584
+ case reflect.Complex128:
585
+ x := v.Complex()
586
+ e.uint64(math.Float64bits(real(x)))
587
+ e.uint64(math.Float64bits(imag(x)))
588
+ }
589
+ }
590
+}
591
+
592
+func (d *decoder) skip(v reflect.Value) {
593
+ d.buf = d.buf[dataSize(v):]
594
+}
595
+
596
+func (e *encoder) skip(v reflect.Value) {
597
+ n := dataSize(v)
598
+ for i := range e.buf[0:n] {
599
+ e.buf[i] = 0
600
+ }
601
+ e.buf = e.buf[n:]
602
+}
603
+
604
+// intDataSize returns the size of the data required to represent the data when encoded.
605
+// It returns zero if the type cannot be implemented by the fast path in Read or Write.
606
+func intDataSize(data interface{}) int {
607
+ switch data := data.(type) {
608
+ case int8, *int8, *uint8:
609
+ return 1
610
+ case []int8:
611
+ return len(data)
612
+ case []uint8:
613
+ return len(data)
614
+ case int16, *int16, *uint16:
615
+ return 2
616
+ case []int16:
617
+ return 2 * len(data)
618
+ case []uint16:
619
+ return 2 * len(data)
620
+ case int32, *int32, *uint32:
621
+ return 4
622
+ case []int32:
623
+ return 4 * len(data)
624
+ case []uint32:
625
+ return 4 * len(data)
626
+ case int64, *int64, *uint64:
627
+ return 8
628
+ case []int64:
629
+ return 8 * len(data)
630
+ case []uint64:
631
+ return 8 * len(data)
632
+ }
633
+ return 0
634
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/disk/disk.go
new
+52
@@ -0,0 +1,52 @@
1
+package disk
2
+
3
+import (
4
+ "encoding/json"
5
+)
6
+
7
+type DiskUsageStat struct {
8
+ Path string `json:"path"`
9
+ Fstype string `json:"fstype"`
10
+ Total uint64 `json:"total"`
11
+ Free uint64 `json:"free"`
12
+ Used uint64 `json:"used"`
13
+ UsedPercent float64 `json:"used_percent"`
14
+ InodesTotal uint64 `json:"inodes_total"`
15
+ InodesUsed uint64 `json:"inodes_used"`
16
+ InodesFree uint64 `json:"inodes_free"`
17
+ InodesUsedPercent float64 `json:"inodes_used_percent"`
18
+}
19
+
20
+type DiskPartitionStat struct {
21
+ Device string `json:"device"`
22
+ Mountpoint string `json:"mountpoint"`
23
+ Fstype string `json:"fstype"`
24
+ Opts string `json:"opts"`
25
+}
26
+
27
+type DiskIOCountersStat struct {
28
+ ReadCount uint64 `json:"read_count"`
29
+ WriteCount uint64 `json:"write_count"`
30
+ ReadBytes uint64 `json:"read_bytes"`
31
+ WriteBytes uint64 `json:"write_bytes"`
32
+ ReadTime uint64 `json:"read_time"`
33
+ WriteTime uint64 `json:"write_time"`
34
+ Name string `json:"name"`
35
+ IoTime uint64 `json:"io_time"`
36
+ SerialNumber string `json:"serial_number"`
37
+}
38
+
39
+func (d DiskUsageStat) String() string {
40
+ s, _ := json.Marshal(d)
41
+ return string(s)
42
+}
43
+
44
+func (d DiskPartitionStat) String() string {
45
+ s, _ := json.Marshal(d)
46
+ return string(s)
47
+}
48
+
49
+func (d DiskIOCountersStat) String() string {
50
+ s, _ := json.Marshal(d)
51
+ return string(s)
52
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/disk/disk_darwin.go
new
+104
@@ -0,0 +1,104 @@
1
+// +build darwin
2
+
3
+package disk
4
+
5
+import (
6
+ "syscall"
7
+ "unsafe"
8
+
9
+ common "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/shirou/gopsutil/common"
10
+)
11
+
12
+func DiskPartitions(all bool) ([]DiskPartitionStat, error) {
13
+ var ret []DiskPartitionStat
14
+
15
+ count, err := Getfsstat(nil, MntWait)
16
+ if err != nil {
17
+ return ret, err
18
+ }
19
+ fs := make([]Statfs_t, count)
20
+ _, err = Getfsstat(fs, MntWait)
21
+ for _, stat := range fs {
22
+ opts := "rw"
23
+ if stat.Flags&MntReadOnly != 0 {
24
+ opts = "ro"
25
+ }
26
+ if stat.Flags&MntSynchronous != 0 {
27
+ opts += ",sync"
28
+ }
29
+ if stat.Flags&MntNoExec != 0 {
30
+ opts += ",noexec"
31
+ }
32
+ if stat.Flags&MntNoSuid != 0 {
33
+ opts += ",nosuid"
34
+ }
35
+ if stat.Flags&MntUnion != 0 {
36
+ opts += ",union"
37
+ }
38
+ if stat.Flags&MntAsync != 0 {
39
+ opts += ",async"
40
+ }
41
+ if stat.Flags&MntSuidDir != 0 {
42
+ opts += ",suiddir"
43
+ }
44
+ if stat.Flags&MntSoftDep != 0 {
45
+ opts += ",softdep"
46
+ }
47
+ if stat.Flags&MntNoSymFollow != 0 {
48
+ opts += ",nosymfollow"
49
+ }
50
+ if stat.Flags&MntGEOMJournal != 0 {
51
+ opts += ",gjounalc"
52
+ }
53
+ if stat.Flags&MntMultilabel != 0 {
54
+ opts += ",multilabel"
55
+ }
56
+ if stat.Flags&MntACLs != 0 {
57
+ opts += ",acls"
58
+ }
59
+ if stat.Flags&MntNoATime != 0 {
60
+ opts += ",noattime"
61
+ }
62
+ if stat.Flags&MntClusterRead != 0 {
63
+ opts += ",nocluster"
64
+ }
65
+ if stat.Flags&MntClusterWrite != 0 {
66
+ opts += ",noclusterw"
67
+ }
68
+ if stat.Flags&MntNFS4ACLs != 0 {
69
+ opts += ",nfs4acls"
70
+ }
71
+ d := DiskPartitionStat{
72
+ Device: common.IntToString(stat.Mntfromname[:]),
73
+ Mountpoint: common.IntToString(stat.Mntonname[:]),
74
+ Fstype: common.IntToString(stat.Fstypename[:]),
75
+ Opts: opts,
76
+ }
77
+ ret = append(ret, d)
78
+ }
79
+
80
+ return ret, nil
81
+}
82
+
83
+func DiskIOCounters() (map[string]DiskIOCountersStat, error) {
84
+ return nil, common.NotImplementedError
85
+}
86
+
87
+func Getfsstat(buf []Statfs_t, flags int) (n int, err error) {
88
+ var _p0 unsafe.Pointer
89
+ var bufsize uintptr
90
+ if len(buf) > 0 {
91
+ _p0 = unsafe.Pointer(&buf[0])
92
+ bufsize = unsafe.Sizeof(Statfs_t{}) * uintptr(len(buf))
93
+ }
94
+ r0, _, e1 := syscall.Syscall(SYS_GETFSSTAT64, uintptr(_p0), bufsize, uintptr(flags))
95
+ n = int(r0)
96
+ if e1 != 0 {
97
+ err = e1
98
+ }
99
+ return
100
+}
101
+
102
+func getFsType(stat syscall.Statfs_t) string {
103
+ return common.IntToString(stat.Fstypename[:])
104
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/disk/disk_darwin_amd64.go
new
+58
@@ -0,0 +1,58 @@
1
+// +build darwin
2
+// +build amd64
3
+
4
+package disk
5
+
6
+const (
7
+ MntWait = 1
8
+ MfsNameLen = 15 /* length of fs type name, not inc. nul */
9
+ MNameLen = 90 /* length of buffer for returned name */
10
+
11
+ MFSTYPENAMELEN = 16 /* length of fs type name including null */
12
+ MAXPATHLEN = 1024
13
+ MNAMELEN = MAXPATHLEN
14
+
15
+ SYS_GETFSSTAT64 = 347
16
+)
17
+
18
+type Fsid struct{ val [2]int32 } /* file system id type */
19
+type uid_t int32
20
+
21
+// sys/mount.h
22
+const (
23
+ MntReadOnly = 0x00000001 /* read only filesystem */
24
+ MntSynchronous = 0x00000002 /* filesystem written synchronously */
25
+ MntNoExec = 0x00000004 /* can't exec from filesystem */
26
+ MntNoSuid = 0x00000008 /* don't honor setuid bits on fs */
27
+ MntUnion = 0x00000020 /* union with underlying filesystem */
28
+ MntAsync = 0x00000040 /* filesystem written asynchronously */
29
+ MntSuidDir = 0x00100000 /* special handling of SUID on dirs */
30
+ MntSoftDep = 0x00200000 /* soft updates being done */
31
+ MntNoSymFollow = 0x00400000 /* do not follow symlinks */
32
+ MntGEOMJournal = 0x02000000 /* GEOM journal support enabled */
33
+ MntMultilabel = 0x04000000 /* MAC support for individual objects */
34
+ MntACLs = 0x08000000 /* ACL support enabled */
35
+ MntNoATime = 0x10000000 /* disable update of file access time */
36
+ MntClusterRead = 0x40000000 /* disable cluster read */
37
+ MntClusterWrite = 0x80000000 /* disable cluster write */
38
+ MntNFS4ACLs = 0x00000010
39
+)
40
+
41
+type Statfs_t struct {
42
+ Bsize uint32
43
+ Iosize int32
44
+ Blocks uint64
45
+ Bfree uint64
46
+ Bavail uint64
47
+ Files uint64
48
+ Ffree uint64
49
+ Fsid Fsid
50
+ Owner uint32
51
+ Type uint32
52
+ Flags uint32
53
+ Fssubtype uint32
54
+ Fstypename [16]int8
55
+ Mntonname [1024]int8
56
+ Mntfromname [1024]int8
57
+ Reserved [8]uint32
58
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/disk/disk_freebsd.go
new
+179
@@ -0,0 +1,179 @@
1
+// +build freebsd
2
+
3
+package disk
4
+
5
+import (
6
+ "bytes"
7
+ "encoding/binary"
8
+ "strconv"
9
+ "syscall"
10
+ "unsafe"
11
+
12
+ common "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/shirou/gopsutil/common"
13
+)
14
+
15
+const (
16
+ CTLKern = 1
17
+ // KernDevstat = 773 // for freebsd 8.4
18
+ // KernDevstatAll = 772 // for freebsd 8.4
19
+ KernDevstat = 974
20
+ KernDevstatAll = 975
21
+)
22
+
23
+func DiskPartitions(all bool) ([]DiskPartitionStat, error) {
24
+ var ret []DiskPartitionStat
25
+
26
+ // get length
27
+ count, err := syscall.Getfsstat(nil, MNT_WAIT)
28
+ if err != nil {
29
+ return ret, err
30
+ }
31
+
32
+ fs := make([]Statfs, count)
33
+ _, err = Getfsstat(fs, MNT_WAIT)
34
+
35
+ for _, stat := range fs {
36
+ opts := "rw"
37
+ if stat.Flags&MNT_RDONLY != 0 {
38
+ opts = "ro"
39
+ }
40
+ if stat.Flags&MNT_SYNCHRONOUS != 0 {
41
+ opts += ",sync"
42
+ }
43
+ if stat.Flags&MNT_NOEXEC != 0 {
44
+ opts += ",noexec"
45
+ }
46
+ if stat.Flags&MNT_NOSUID != 0 {
47
+ opts += ",nosuid"
48
+ }
49
+ if stat.Flags&MNT_UNION != 0 {
50
+ opts += ",union"
51
+ }
52
+ if stat.Flags&MNT_ASYNC != 0 {
53
+ opts += ",async"
54
+ }
55
+ if stat.Flags&MNT_SUIDDIR != 0 {
56
+ opts += ",suiddir"
57
+ }
58
+ if stat.Flags&MNT_SOFTDEP != 0 {
59
+ opts += ",softdep"
60
+ }
61
+ if stat.Flags&MNT_NOSYMFOLLOW != 0 {
62
+ opts += ",nosymfollow"
63
+ }
64
+ if stat.Flags&MNT_GJOURNAL != 0 {
65
+ opts += ",gjounalc"
66
+ }
67
+ if stat.Flags&MNT_MULTILABEL != 0 {
68
+ opts += ",multilabel"
69
+ }
70
+ if stat.Flags&MNT_ACLS != 0 {
71
+ opts += ",acls"
72
+ }
73
+ if stat.Flags&MNT_NOATIME != 0 {
74
+ opts += ",noattime"
75
+ }
76
+ if stat.Flags&MNT_NOCLUSTERR != 0 {
77
+ opts += ",nocluster"
78
+ }
79
+ if stat.Flags&MNT_NOCLUSTERW != 0 {
80
+ opts += ",noclusterw"
81
+ }
82
+ if stat.Flags&MNT_NFS4ACLS != 0 {
83
+ opts += ",nfs4acls"
84
+ }
85
+
86
+ d := DiskPartitionStat{
87
+ Device: common.IntToString(stat.Mntfromname[:]),
88
+ Mountpoint: common.IntToString(stat.Mntonname[:]),
89
+ Fstype: common.IntToString(stat.Fstypename[:]),
90
+ Opts: opts,
91
+ }
92
+ ret = append(ret, d)
93
+ }
94
+
95
+ return ret, nil
96
+}
97
+
98
+func DiskIOCounters() (map[string]DiskIOCountersStat, error) {
99
+ // statinfo->devinfo->devstat
100
+ // /usr/include/devinfo.h
101
+
102
+ // sysctl.sysctl ('kern.devstat.all', 0)
103
+ ret := make(map[string]DiskIOCountersStat)
104
+ mib := []int32{CTLKern, KernDevstat, KernDevstatAll}
105
+
106
+ buf, length, err := common.CallSyscall(mib)
107
+ if err != nil {
108
+ return nil, err
109
+ }
110
+
111
+ ds := Devstat{}
112
+ devstatLen := int(unsafe.Sizeof(ds))
113
+ count := int(length / uint64(devstatLen))
114
+
115
+ buf = buf[8:] // devstat.all has version in the head.
116
+ // parse buf to Devstat
117
+ for i := 0; i < count; i++ {
118
+ b := buf[i*devstatLen : i*devstatLen+devstatLen]
119
+ d, err := parseDevstat(b)
120
+ if err != nil {
121
+ continue
122
+ }
123
+ un := strconv.Itoa(int(d.Unit_number))
124
+ name := common.IntToString(d.Device_name[:]) + un
125
+
126
+ ds := DiskIOCountersStat{
127
+ ReadCount: d.Operations[DEVSTAT_READ],
128
+ WriteCount: d.Operations[DEVSTAT_WRITE],
129
+ ReadBytes: d.Bytes[DEVSTAT_READ],
130
+ WriteBytes: d.Bytes[DEVSTAT_WRITE],
131
+ ReadTime: d.Duration[DEVSTAT_READ].Compute(),
132
+ WriteTime: d.Duration[DEVSTAT_WRITE].Compute(),
133
+ Name: name,
134
+ }
135
+ ret[name] = ds
136
+ }
137
+
138
+ return ret, nil
139
+}
140
+
141
+func (b Bintime) Compute() uint64 {
142
+ BINTIME_SCALE := 5.42101086242752217003726400434970855712890625e-20
143
+ return uint64(b.Sec) + b.Frac*uint64(BINTIME_SCALE)
144
+}
145
+
146
+// BT2LD(time) ((long double)(time).sec + (time).frac * BINTIME_SCALE)
147
+
148
+// Getfsstat is borrowed from pkg/syscall/syscall_freebsd.go
149
+// change Statfs_t to Statfs in order to get more information
150
+func Getfsstat(buf []Statfs, flags int) (n int, err error) {
151
+ var _p0 unsafe.Pointer
152
+ var bufsize uintptr
153
+ if len(buf) > 0 {
154
+ _p0 = unsafe.Pointer(&buf[0])
155
+ bufsize = unsafe.Sizeof(Statfs{}) * uintptr(len(buf))
156
+ }
157
+ r0, _, e1 := syscall.Syscall(syscall.SYS_GETFSSTAT, uintptr(_p0), bufsize, uintptr(flags))
158
+ n = int(r0)
159
+ if e1 != 0 {
160
+ err = e1
161
+ }
162
+ return
163
+}
164
+
165
+func parseDevstat(buf []byte) (Devstat, error) {
166
+ var ds Devstat
167
+ br := bytes.NewReader(buf)
168
+ // err := binary.Read(br, binary.LittleEndian, &ds)
169
+ err := Read(br, binary.LittleEndian, &ds)
170
+ if err != nil {
171
+ return ds, err
172
+ }
173
+
174
+ return ds, nil
175
+}
176
+
177
+func getFsType(stat syscall.Statfs_t) string {
178
+ return common.IntToString(stat.Fstypename[:])
179
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/disk/disk_freebsd_amd64.go
new
+111
@@ -0,0 +1,111 @@
1
+// Created by cgo -godefs - DO NOT EDIT
2
+// cgo -godefs types_freebsd.go
3
+
4
+package disk
5
+
6
+const (
7
+ sizeofPtr = 0x8
8
+ sizeofShort = 0x2
9
+ sizeofInt = 0x4
10
+ sizeofLong = 0x8
11
+ sizeofLongLong = 0x8
12
+ sizeofLongDouble = 0x8
13
+
14
+ DEVSTAT_NO_DATA = 0x00
15
+ DEVSTAT_READ = 0x01
16
+ DEVSTAT_WRITE = 0x02
17
+ DEVSTAT_FREE = 0x03
18
+
19
+ MNT_RDONLY = 0x00000001
20
+ MNT_SYNCHRONOUS = 0x00000002
21
+ MNT_NOEXEC = 0x00000004
22
+ MNT_NOSUID = 0x00000008
23
+ MNT_UNION = 0x00000020
24
+ MNT_ASYNC = 0x00000040
25
+ MNT_SUIDDIR = 0x00100000
26
+ MNT_SOFTDEP = 0x00200000
27
+ MNT_NOSYMFOLLOW = 0x00400000
28
+ MNT_GJOURNAL = 0x02000000
29
+ MNT_MULTILABEL = 0x04000000
30
+ MNT_ACLS = 0x08000000
31
+ MNT_NOATIME = 0x10000000
32
+ MNT_NOCLUSTERR = 0x40000000
33
+ MNT_NOCLUSTERW = 0x80000000
34
+ MNT_NFS4ACLS = 0x00000010
35
+
36
+ MNT_WAIT = 1
37
+ MNT_NOWAIT = 2
38
+ MNT_LAZY = 3
39
+ MNT_SUSPEND = 4
40
+)
41
+
42
+type (
43
+ _C_short int16
44
+ _C_int int32
45
+ _C_long int64
46
+ _C_long_long int64
47
+ _C_long_double int64
48
+)
49
+
50
+type Statfs struct {
51
+ Version uint32
52
+ Type uint32
53
+ Flags uint64
54
+ Bsize uint64
55
+ Iosize uint64
56
+ Blocks uint64
57
+ Bfree uint64
58
+ Bavail int64
59
+ Files uint64
60
+ Ffree int64
61
+ Syncwrites uint64
62
+ Asyncwrites uint64
63
+ Syncreads uint64
64
+ Asyncreads uint64
65
+ Spare [10]uint64
66
+ Namemax uint32
67
+ Owner uint32
68
+ Fsid Fsid
69
+ Charspare [80]int8
70
+ Fstypename [16]int8
71
+ Mntfromname [88]int8
72
+ Mntonname [88]int8
73
+}
74
+type Fsid struct {
75
+ Val [2]int32
76
+}
77
+
78
+type Devstat struct {
79
+ Sequence0 uint32
80
+ Allocated int32
81
+ Start_count uint32
82
+ End_count uint32
83
+ Busy_from Bintime
84
+ Dev_links _Ctype_struct___0
85
+ Device_number uint32
86
+ Device_name [16]int8
87
+ Unit_number int32
88
+ Bytes [4]uint64
89
+ Operations [4]uint64
90
+ Duration [4]Bintime
91
+ Busy_time Bintime
92
+ Creation_time Bintime
93
+ Block_size uint32
94
+ Pad_cgo_0 [4]byte
95
+ Tag_types [3]uint64
96
+ Flags uint32
97
+ Device_type uint32
98
+ Priority uint32
99
+ Pad_cgo_1 [4]byte
100
+ Id *byte
101
+ Sequence1 uint32
102
+ Pad_cgo_2 [4]byte
103
+}
104
+type Bintime struct {
105
+ Sec int64
106
+ Frac uint64
107
+}
108
+
109
+type _Ctype_struct___0 struct {
110
+ Empty uint64
111
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/disk/disk_linux.go
new
+327
@@ -0,0 +1,327 @@
1
+// +build linux
2
+
3
+package disk
4
+
5
+import (
6
+ "fmt"
7
+ "os/exec"
8
+ "strconv"
9
+ "strings"
10
+ "syscall"
11
+
12
+ common "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/shirou/gopsutil/common"
13
+)
14
+
15
+const (
16
+ SectorSize = 512
17
+)
18
+const (
19
+ // man statfs
20
+ ADFS_SUPER_MAGIC = 0xadf5
21
+ AFFS_SUPER_MAGIC = 0xADFF
22
+ BDEVFS_MAGIC = 0x62646576
23
+ BEFS_SUPER_MAGIC = 0x42465331
24
+ BFS_MAGIC = 0x1BADFACE
25
+ BINFMTFS_MAGIC = 0x42494e4d
26
+ BTRFS_SUPER_MAGIC = 0x9123683E
27
+ CGROUP_SUPER_MAGIC = 0x27e0eb
28
+ CIFS_MAGIC_NUMBER = 0xFF534D42
29
+ CODA_SUPER_MAGIC = 0x73757245
30
+ COH_SUPER_MAGIC = 0x012FF7B7
31
+ CRAMFS_MAGIC = 0x28cd3d45
32
+ DEBUGFS_MAGIC = 0x64626720
33
+ DEVFS_SUPER_MAGIC = 0x1373
34
+ DEVPTS_SUPER_MAGIC = 0x1cd1
35
+ EFIVARFS_MAGIC = 0xde5e81e4
36
+ EFS_SUPER_MAGIC = 0x00414A53
37
+ EXT_SUPER_MAGIC = 0x137D
38
+ EXT2_OLD_SUPER_MAGIC = 0xEF51
39
+ EXT2_SUPER_MAGIC = 0xEF53
40
+ EXT3_SUPER_MAGIC = 0xEF53
41
+ EXT4_SUPER_MAGIC = 0xEF53
42
+ FUSE_SUPER_MAGIC = 0x65735546
43
+ FUTEXFS_SUPER_MAGIC = 0xBAD1DEA
44
+ HFS_SUPER_MAGIC = 0x4244
45
+ HOSTFS_SUPER_MAGIC = 0x00c0ffee
46
+ HPFS_SUPER_MAGIC = 0xF995E849
47
+ HUGETLBFS_MAGIC = 0x958458f6
48
+ ISOFS_SUPER_MAGIC = 0x9660
49
+ JFFS2_SUPER_MAGIC = 0x72b6
50
+ JFS_SUPER_MAGIC = 0x3153464a
51
+ MINIX_SUPER_MAGIC = 0x137F /* orig. minix */
52
+ MINIX_SUPER_MAGIC2 = 0x138F /* 30 char minix */
53
+ MINIX2_SUPER_MAGIC = 0x2468 /* minix V2 */
54
+ MINIX2_SUPER_MAGIC2 = 0x2478 /* minix V2, 30 char names */
55
+ MINIX3_SUPER_MAGIC = 0x4d5a /* minix V3 fs, 60 char names */
56
+ MQUEUE_MAGIC = 0x19800202
57
+ MSDOS_SUPER_MAGIC = 0x4d44
58
+ NCP_SUPER_MAGIC = 0x564c
59
+ NFS_SUPER_MAGIC = 0x6969
60
+ NILFS_SUPER_MAGIC = 0x3434
61
+ NTFS_SB_MAGIC = 0x5346544e
62
+ OCFS2_SUPER_MAGIC = 0x7461636f
63
+ OPENPROM_SUPER_MAGIC = 0x9fa1
64
+ PIPEFS_MAGIC = 0x50495045
65
+ PROC_SUPER_MAGIC = 0x9fa0
66
+ PSTOREFS_MAGIC = 0x6165676C
67
+ QNX4_SUPER_MAGIC = 0x002f
68
+ QNX6_SUPER_MAGIC = 0x68191122
69
+ RAMFS_MAGIC = 0x858458f6
70
+ REISERFS_SUPER_MAGIC = 0x52654973
71
+ ROMFS_MAGIC = 0x7275
72
+ SELINUX_MAGIC = 0xf97cff8c
73
+ SMACK_MAGIC = 0x43415d53
74
+ SMB_SUPER_MAGIC = 0x517B
75
+ SOCKFS_MAGIC = 0x534F434B
76
+ SQUASHFS_MAGIC = 0x73717368
77
+ SYSFS_MAGIC = 0x62656572
78
+ SYSV2_SUPER_MAGIC = 0x012FF7B6
79
+ SYSV4_SUPER_MAGIC = 0x012FF7B5
80
+ TMPFS_MAGIC = 0x01021994
81
+ UDF_SUPER_MAGIC = 0x15013346
82
+ UFS_MAGIC = 0x00011954
83
+ USBDEVICE_SUPER_MAGIC = 0x9fa2
84
+ V9FS_MAGIC = 0x01021997
85
+ VXFS_SUPER_MAGIC = 0xa501FCF5
86
+ XENFS_SUPER_MAGIC = 0xabba1974
87
+ XENIX_SUPER_MAGIC = 0x012FF7B4
88
+ XFS_SUPER_MAGIC = 0x58465342
89
+ _XIAFS_SUPER_MAGIC = 0x012FD16D
90
+
91
+ AFS_SUPER_MAGIC = 0x5346414F
92
+ AUFS_SUPER_MAGIC = 0x61756673
93
+ ANON_INODE_FS_SUPER_MAGIC = 0x09041934
94
+ CEPH_SUPER_MAGIC = 0x00C36400
95
+ ECRYPTFS_SUPER_MAGIC = 0xF15F
96
+ FAT_SUPER_MAGIC = 0x4006
97
+ FHGFS_SUPER_MAGIC = 0x19830326
98
+ FUSEBLK_SUPER_MAGIC = 0x65735546
99
+ FUSECTL_SUPER_MAGIC = 0x65735543
100
+ GFS_SUPER_MAGIC = 0x1161970
101
+ GPFS_SUPER_MAGIC = 0x47504653
102
+ MTD_INODE_FS_SUPER_MAGIC = 0x11307854
103
+ INOTIFYFS_SUPER_MAGIC = 0x2BAD1DEA
104
+ ISOFS_R_WIN_SUPER_MAGIC = 0x4004
105
+ ISOFS_WIN_SUPER_MAGIC = 0x4000
106
+ JFFS_SUPER_MAGIC = 0x07C0
107
+ KAFS_SUPER_MAGIC = 0x6B414653
108
+ LUSTRE_SUPER_MAGIC = 0x0BD00BD0
109
+ NFSD_SUPER_MAGIC = 0x6E667364
110
+ PANFS_SUPER_MAGIC = 0xAAD7AAEA
111
+ RPC_PIPEFS_SUPER_MAGIC = 0x67596969
112
+ SECURITYFS_SUPER_MAGIC = 0x73636673
113
+ UFS_BYTESWAPPED_SUPER_MAGIC = 0x54190100
114
+ VMHGFS_SUPER_MAGIC = 0xBACBACBC
115
+ VZFS_SUPER_MAGIC = 0x565A4653
116
+ ZFS_SUPER_MAGIC = 0x2FC12FC1
117
+)
118
+
119
+// coreutils/src/stat.c
120
+var fsTypeMap = map[int64]string{
121
+ ADFS_SUPER_MAGIC: "adfs", /* 0xADF5 local */
122
+ AFFS_SUPER_MAGIC: "affs", /* 0xADFF local */
123
+ AFS_SUPER_MAGIC: "afs", /* 0x5346414F remote */
124
+ ANON_INODE_FS_SUPER_MAGIC: "anon-inode FS", /* 0x09041934 local */
125
+ AUFS_SUPER_MAGIC: "aufs", /* 0x61756673 remote */
126
+ // AUTOFS_SUPER_MAGIC: "autofs", /* 0x0187 local */
127
+ BEFS_SUPER_MAGIC: "befs", /* 0x42465331 local */
128
+ BDEVFS_MAGIC: "bdevfs", /* 0x62646576 local */
129
+ BFS_MAGIC: "bfs", /* 0x1BADFACE local */
130
+ BINFMTFS_MAGIC: "binfmt_misc", /* 0x42494E4D local */
131
+ BTRFS_SUPER_MAGIC: "btrfs", /* 0x9123683E local */
132
+ CEPH_SUPER_MAGIC: "ceph", /* 0x00C36400 remote */
133
+ CGROUP_SUPER_MAGIC: "cgroupfs", /* 0x0027E0EB local */
134
+ CIFS_MAGIC_NUMBER: "cifs", /* 0xFF534D42 remote */
135
+ CODA_SUPER_MAGIC: "coda", /* 0x73757245 remote */
136
+ COH_SUPER_MAGIC: "coh", /* 0x012FF7B7 local */
137
+ CRAMFS_MAGIC: "cramfs", /* 0x28CD3D45 local */
138
+ DEBUGFS_MAGIC: "debugfs", /* 0x64626720 local */
139
+ DEVFS_SUPER_MAGIC: "devfs", /* 0x1373 local */
140
+ DEVPTS_SUPER_MAGIC: "devpts", /* 0x1CD1 local */
141
+ ECRYPTFS_SUPER_MAGIC: "ecryptfs", /* 0xF15F local */
142
+ EFS_SUPER_MAGIC: "efs", /* 0x00414A53 local */
143
+ EXT_SUPER_MAGIC: "ext", /* 0x137D local */
144
+ EXT2_SUPER_MAGIC: "ext2/ext3", /* 0xEF53 local */
145
+ EXT2_OLD_SUPER_MAGIC: "ext2", /* 0xEF51 local */
146
+ FAT_SUPER_MAGIC: "fat", /* 0x4006 local */
147
+ FHGFS_SUPER_MAGIC: "fhgfs", /* 0x19830326 remote */
148
+ FUSEBLK_SUPER_MAGIC: "fuseblk", /* 0x65735546 remote */
149
+ FUSECTL_SUPER_MAGIC: "fusectl", /* 0x65735543 remote */
150
+ FUTEXFS_SUPER_MAGIC: "futexfs", /* 0x0BAD1DEA local */
151
+ GFS_SUPER_MAGIC: "gfs/gfs2", /* 0x1161970 remote */
152
+ GPFS_SUPER_MAGIC: "gpfs", /* 0x47504653 remote */
153
+ HFS_SUPER_MAGIC: "hfs", /* 0x4244 local */
154
+ HPFS_SUPER_MAGIC: "hpfs", /* 0xF995E849 local */
155
+ HUGETLBFS_MAGIC: "hugetlbfs", /* 0x958458F6 local */
156
+ MTD_INODE_FS_SUPER_MAGIC: "inodefs", /* 0x11307854 local */
157
+ INOTIFYFS_SUPER_MAGIC: "inotifyfs", /* 0x2BAD1DEA local */
158
+ ISOFS_SUPER_MAGIC: "isofs", /* 0x9660 local */
159
+ ISOFS_R_WIN_SUPER_MAGIC: "isofs", /* 0x4004 local */
160
+ ISOFS_WIN_SUPER_MAGIC: "isofs", /* 0x4000 local */
161
+ JFFS_SUPER_MAGIC: "jffs", /* 0x07C0 local */
162
+ JFFS2_SUPER_MAGIC: "jffs2", /* 0x72B6 local */
163
+ JFS_SUPER_MAGIC: "jfs", /* 0x3153464A local */
164
+ KAFS_SUPER_MAGIC: "k-afs", /* 0x6B414653 remote */
165
+ LUSTRE_SUPER_MAGIC: "lustre", /* 0x0BD00BD0 remote */
166
+ MINIX_SUPER_MAGIC: "minix", /* 0x137F local */
167
+ MINIX_SUPER_MAGIC2: "minix (30 char.)", /* 0x138F local */
168
+ MINIX2_SUPER_MAGIC: "minix v2", /* 0x2468 local */
169
+ MINIX2_SUPER_MAGIC2: "minix v2 (30 char.)", /* 0x2478 local */
170
+ MINIX3_SUPER_MAGIC: "minix3", /* 0x4D5A local */
171
+ MQUEUE_MAGIC: "mqueue", /* 0x19800202 local */
172
+ MSDOS_SUPER_MAGIC: "msdos", /* 0x4D44 local */
173
+ NCP_SUPER_MAGIC: "novell", /* 0x564C remote */
174
+ NFS_SUPER_MAGIC: "nfs", /* 0x6969 remote */
175
+ NFSD_SUPER_MAGIC: "nfsd", /* 0x6E667364 remote */
176
+ NILFS_SUPER_MAGIC: "nilfs", /* 0x3434 local */
177
+ NTFS_SB_MAGIC: "ntfs", /* 0x5346544E local */
178
+ OPENPROM_SUPER_MAGIC: "openprom", /* 0x9FA1 local */
179
+ OCFS2_SUPER_MAGIC: "ocfs2", /* 0x7461636f remote */
180
+ PANFS_SUPER_MAGIC: "panfs", /* 0xAAD7AAEA remote */
181
+ PIPEFS_MAGIC: "pipefs", /* 0x50495045 remote */
182
+ PROC_SUPER_MAGIC: "proc", /* 0x9FA0 local */
183
+ PSTOREFS_MAGIC: "pstorefs", /* 0x6165676C local */
184
+ QNX4_SUPER_MAGIC: "qnx4", /* 0x002F local */
185
+ QNX6_SUPER_MAGIC: "qnx6", /* 0x68191122 local */
186
+ RAMFS_MAGIC: "ramfs", /* 0x858458F6 local */
187
+ REISERFS_SUPER_MAGIC: "reiserfs", /* 0x52654973 local */
188
+ ROMFS_MAGIC: "romfs", /* 0x7275 local */
189
+ RPC_PIPEFS_SUPER_MAGIC: "rpc_pipefs", /* 0x67596969 local */
190
+ SECURITYFS_SUPER_MAGIC: "securityfs", /* 0x73636673 local */
191
+ SELINUX_MAGIC: "selinux", /* 0xF97CFF8C local */
192
+ SMB_SUPER_MAGIC: "smb", /* 0x517B remote */
193
+ SOCKFS_MAGIC: "sockfs", /* 0x534F434B local */
194
+ SQUASHFS_MAGIC: "squashfs", /* 0x73717368 local */
195
+ SYSFS_MAGIC: "sysfs", /* 0x62656572 local */
196
+ SYSV2_SUPER_MAGIC: "sysv2", /* 0x012FF7B6 local */
197
+ SYSV4_SUPER_MAGIC: "sysv4", /* 0x012FF7B5 local */
198
+ TMPFS_MAGIC: "tmpfs", /* 0x01021994 local */
199
+ UDF_SUPER_MAGIC: "udf", /* 0x15013346 local */
200
+ UFS_MAGIC: "ufs", /* 0x00011954 local */
201
+ UFS_BYTESWAPPED_SUPER_MAGIC: "ufs", /* 0x54190100 local */
202
+ USBDEVICE_SUPER_MAGIC: "usbdevfs", /* 0x9FA2 local */
203
+ V9FS_MAGIC: "v9fs", /* 0x01021997 local */
204
+ VMHGFS_SUPER_MAGIC: "vmhgfs", /* 0xBACBACBC remote */
205
+ VXFS_SUPER_MAGIC: "vxfs", /* 0xA501FCF5 local */
206
+ VZFS_SUPER_MAGIC: "vzfs", /* 0x565A4653 local */
207
+ XENFS_SUPER_MAGIC: "xenfs", /* 0xABBA1974 local */
208
+ XENIX_SUPER_MAGIC: "xenix", /* 0x012FF7B4 local */
209
+ XFS_SUPER_MAGIC: "xfs", /* 0x58465342 local */
210
+ _XIAFS_SUPER_MAGIC: "xia", /* 0x012FD16D local */
211
+ ZFS_SUPER_MAGIC: "zfs", /* 0x2FC12FC1 local */
212
+}
213
+
214
+// Get disk partitions.
215
+// should use setmntent(3) but this implement use /etc/mtab file
216
+func DiskPartitions(all bool) ([]DiskPartitionStat, error) {
217
+
218
+ filename := "/etc/mtab"
219
+ lines, err := common.ReadLines(filename)
220
+ if err != nil {
221
+ return nil, err
222
+ }
223
+
224
+ ret := make([]DiskPartitionStat, 0, len(lines))
225
+
226
+ for _, line := range lines {
227
+ fields := strings.Fields(line)
228
+ d := DiskPartitionStat{
229
+ Device: fields[0],
230
+ Mountpoint: fields[1],
231
+ Fstype: fields[2],
232
+ Opts: fields[3],
233
+ }
234
+ ret = append(ret, d)
235
+ }
236
+
237
+ return ret, nil
238
+}
239
+
240
+func DiskIOCounters() (map[string]DiskIOCountersStat, error) {
241
+ filename := "/proc/diskstats"
242
+ lines, err := common.ReadLines(filename)
243
+ if err != nil {
244
+ return nil, err
245
+ }
246
+ ret := make(map[string]DiskIOCountersStat, 0)
247
+ empty := DiskIOCountersStat{}
248
+
249
+ for _, line := range lines {
250
+ fields := strings.Fields(line)
251
+ name := fields[2]
252
+ reads, err := strconv.ParseUint((fields[3]), 10, 64)
253
+ if err != nil {
254
+ return ret, err
255
+ }
256
+ rbytes, err := strconv.ParseUint((fields[5]), 10, 64)
257
+ if err != nil {
258
+ return ret, err
259
+ }
260
+ rtime, err := strconv.ParseUint((fields[6]), 10, 64)
261
+ if err != nil {
262
+ return ret, err
263
+ }
264
+ writes, err := strconv.ParseUint((fields[7]), 10, 64)
265
+ if err != nil {
266
+ return ret, err
267
+ }
268
+ wbytes, err := strconv.ParseUint((fields[9]), 10, 64)
269
+ if err != nil {
270
+ return ret, err
271
+ }
272
+ wtime, err := strconv.ParseUint((fields[10]), 10, 64)
273
+ if err != nil {
274
+ return ret, err
275
+ }
276
+ iotime, err := strconv.ParseUint((fields[12]), 10, 64)
277
+ if err != nil {
278
+ return ret, err
279
+ }
280
+ d := DiskIOCountersStat{
281
+ ReadBytes: rbytes * SectorSize,
282
+ WriteBytes: wbytes * SectorSize,
283
+ ReadCount: reads,
284
+ WriteCount: writes,
285
+ ReadTime: rtime,
286
+ WriteTime: wtime,
287
+ IoTime: iotime,
288
+ }
289
+ if d == empty {
290
+ continue
291
+ }
292
+ d.Name = name
293
+
294
+ d.SerialNumber = GetDiskSerialNumber(name)
295
+ ret[name] = d
296
+ }
297
+ return ret, nil
298
+}
299
+
300
+func GetDiskSerialNumber(name string) string {
301
+ n := fmt.Sprintf("--name=%s", name)
302
+ out, err := exec.Command("/sbin/udevadm", "info", "--query=property", n).Output()
303
+
304
+ // does not return error, just an empty string
305
+ if err != nil {
306
+ return ""
307
+ }
308
+ lines := strings.Split(string(out), "\n")
309
+ for _, line := range lines {
310
+ values := strings.Split(line, "=")
311
+ if len(values) < 2 || values[0] != "ID_SERIAL" {
312
+ // only get ID_SERIAL, not ID_SERIAL_SHORT
313
+ continue
314
+ }
315
+ return values[1]
316
+ }
317
+ return ""
318
+}
319
+
320
+func getFsType(stat syscall.Statfs_t) string {
321
+ t := int64(stat.Type)
322
+ ret, ok := fsTypeMap[t]
323
+ if !ok {
324
+ return ""
325
+ }
326
+ return ret
327
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/disk/disk_test.go
new
+97
@@ -0,0 +1,97 @@
1
+package disk
2
+
3
+import (
4
+ "fmt"
5
+ "runtime"
6
+ "testing"
7
+)
8
+
9
+func TestDisk_usage(t *testing.T) {
10
+ path := "/"
11
+ if runtime.GOOS == "windows" {
12
+ path = "C:"
13
+ }
14
+ v, err := DiskUsage(path)
15
+ if err != nil {
16
+ t.Errorf("error %v", err)
17
+ }
18
+ if v.Path != path {
19
+ t.Errorf("error %v", err)
20
+ }
21
+}
22
+
23
+func TestDisk_partitions(t *testing.T) {
24
+ ret, err := DiskPartitions(false)
25
+ if err != nil || len(ret) == 0 {
26
+ t.Errorf("error %v", err)
27
+ }
28
+ empty := DiskPartitionStat{}
29
+ for _, disk := range ret {
30
+ if disk == empty {
31
+ t.Errorf("Could not get device info %v", disk)
32
+ }
33
+ }
34
+}
35
+
36
+func TestDisk_io_counters(t *testing.T) {
37
+ ret, err := DiskIOCounters()
38
+ if err != nil {
39
+ t.Errorf("error %v", err)
40
+ }
41
+ if len(ret) == 0 {
42
+ t.Errorf("ret is empty, %v", ret)
43
+ }
44
+ empty := DiskIOCountersStat{}
45
+ for part, io := range ret {
46
+ if io == empty {
47
+ t.Errorf("io_counter error %v, %v", part, io)
48
+ }
49
+ }
50
+}
51
+
52
+func TestDiskUsageStat_String(t *testing.T) {
53
+ v := DiskUsageStat{
54
+ Path: "/",
55
+ Total: 1000,
56
+ Free: 2000,
57
+ Used: 3000,
58
+ UsedPercent: 50.1,
59
+ InodesTotal: 4000,
60
+ InodesUsed: 5000,
61
+ InodesFree: 6000,
62
+ InodesUsedPercent: 49.1,
63
+ Fstype: "ext4",
64
+ }
65
+ e := `{"path":"/","fstype":"ext4","total":1000,"free":2000,"used":3000,"used_percent":50.1,"inodes_total":4000,"inodes_used":5000,"inodes_free":6000,"inodes_used_percent":49.1}`
66
+ if e != fmt.Sprintf("%v", v) {
67
+ t.Errorf("DiskUsageStat string is invalid: %v", v)
68
+ }
69
+}
70
+
71
+func TestDiskPartitionStat_String(t *testing.T) {
72
+ v := DiskPartitionStat{
73
+ Device: "sd01",
74
+ Mountpoint: "/",
75
+ Fstype: "ext4",
76
+ Opts: "ro",
77
+ }
78
+ e := `{"device":"sd01","mountpoint":"/","fstype":"ext4","opts":"ro"}`
79
+ if e != fmt.Sprintf("%v", v) {
80
+ t.Errorf("DiskUsageStat string is invalid: %v", v)
81
+ }
82
+}
83
+
84
+func TestDiskIOCountersStat_String(t *testing.T) {
85
+ v := DiskIOCountersStat{
86
+ Name: "sd01",
87
+ ReadCount: 100,
88
+ WriteCount: 200,
89
+ ReadBytes: 300,
90
+ WriteBytes: 400,
91
+ SerialNumber: "SERIAL",
92
+ }
93
+ e := `{"read_count":100,"write_count":200,"read_bytes":300,"write_bytes":400,"read_time":0,"write_time":0,"name":"sd01","io_time":0,"serial_number":"SERIAL"}`
94
+ if e != fmt.Sprintf("%v", v) {
95
+ t.Errorf("DiskUsageStat string is invalid: %v", v)
96
+ }
97
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/disk/disk_unix.go
new
+30
@@ -0,0 +1,30 @@
1
+// +build freebsd linux darwin
2
+
3
+package disk
4
+
5
+import "syscall"
6
+
7
+func DiskUsage(path string) (*DiskUsageStat, error) {
8
+ stat := syscall.Statfs_t{}
9
+ err := syscall.Statfs(path, &stat)
10
+ if err != nil {
11
+ return nil, err
12
+ }
13
+ bsize := stat.Bsize
14
+
15
+ ret := &DiskUsageStat{
16
+ Path: path,
17
+ Fstype: getFsType(stat),
18
+ Total: (uint64(stat.Blocks) * uint64(bsize)),
19
+ Free: (uint64(stat.Bfree) * uint64(bsize)),
20
+ InodesTotal: (uint64(stat.Files)),
21
+ InodesFree: (uint64(stat.Ffree)),
22
+ }
23
+
24
+ ret.InodesUsed = (ret.InodesTotal - ret.InodesFree)
25
+ ret.InodesUsedPercent = (float64(ret.InodesUsed) / float64(ret.InodesTotal)) * 100.0
26
+ ret.Used = (uint64(stat.Blocks) - uint64(stat.Bfree)) * uint64(bsize)
27
+ ret.UsedPercent = (float64(ret.Used) / float64(ret.Total)) * 100.0
28
+
29
+ return ret, nil
30
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/disk/disk_windows.go
new
+155
@@ -0,0 +1,155 @@
1
+// +build windows
2
+
3
+package disk
4
+
5
+import (
6
+ "bytes"
7
+ "syscall"
8
+ "unsafe"
9
+
10
+ "github.com/StackExchange/wmi"
11
+
12
+ common "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/shirou/gopsutil/common"
13
+)
14
+
15
+var (
16
+ procGetDiskFreeSpaceExW = common.Modkernel32.NewProc("GetDiskFreeSpaceExW")
17
+ procGetLogicalDriveStringsW = common.Modkernel32.NewProc("GetLogicalDriveStringsW")
18
+ procGetDriveType = common.Modkernel32.NewProc("GetDriveTypeW")
19
+ provGetVolumeInformation = common.Modkernel32.NewProc("GetVolumeInformationW")
20
+)
21
+
22
+var (
23
+ FileFileCompression = int64(16) // 0x00000010
24
+ FileReadOnlyVolume = int64(524288) // 0x00080000
25
+)
26
+
27
+type Win32_PerfFormattedData struct {
28
+ Name string
29
+ AvgDiskBytesPerRead uint64
30
+ AvgDiskBytesPerWrite uint64
31
+ AvgDiskReadQueueLength uint64
32
+ AvgDiskWriteQueueLength uint64
33
+ AvgDisksecPerRead uint64
34
+ AvgDisksecPerWrite uint64
35
+}
36
+
37
+const WaitMSec = 500
38
+
39
+func DiskUsage(path string) (*DiskUsageStat, error) {
40
+ ret := &DiskUsageStat{}
41
+
42
+ lpFreeBytesAvailable := int64(0)
43
+ lpTotalNumberOfBytes := int64(0)
44
+ lpTotalNumberOfFreeBytes := int64(0)
45
+ diskret, _, err := procGetDiskFreeSpaceExW.Call(
46
+ uintptr(unsafe.Pointer(syscall.StringToUTF16Ptr(path))),
47
+ uintptr(unsafe.Pointer(&lpFreeBytesAvailable)),
48
+ uintptr(unsafe.Pointer(&lpTotalNumberOfBytes)),
49
+ uintptr(unsafe.Pointer(&lpTotalNumberOfFreeBytes)))
50
+ if diskret == 0 {
51
+ return nil, err
52
+ }
53
+ ret = &DiskUsageStat{
54
+ Path: path,
55
+ Total: uint64(lpTotalNumberOfBytes),
56
+ Free: uint64(lpTotalNumberOfFreeBytes),
57
+ Used: uint64(lpTotalNumberOfBytes) - uint64(lpTotalNumberOfFreeBytes),
58
+ UsedPercent: (float64(lpTotalNumberOfBytes) - float64(lpTotalNumberOfFreeBytes)) / float64(lpTotalNumberOfBytes) * 100,
59
+ // InodesTotal: 0,
60
+ // InodesFree: 0,
61
+ // InodesUsed: 0,
62
+ // InodesUsedPercent: 0,
63
+ }
64
+ return ret, nil
65
+}
66
+
67
+func DiskPartitions(all bool) ([]DiskPartitionStat, error) {
68
+ var ret []DiskPartitionStat
69
+ lpBuffer := make([]byte, 254)
70
+ diskret, _, err := procGetLogicalDriveStringsW.Call(
71
+ uintptr(len(lpBuffer)),
72
+ uintptr(unsafe.Pointer(&lpBuffer[0])))
73
+ if diskret == 0 {
74
+ return ret, err
75
+ }
76
+ for _, v := range lpBuffer {
77
+ if v >= 65 && v <= 90 {
78
+ path := string(v) + ":"
79
+ if path == "A:" || path == "B:" { // skip floppy drives
80
+ continue
81
+ }
82
+ typepath, _ := syscall.UTF16PtrFromString(path)
83
+ typeret, _, _ := procGetDriveType.Call(uintptr(unsafe.Pointer(typepath)))
84
+ if typeret == 0 {
85
+ return ret, syscall.GetLastError()
86
+ }
87
+ // 2: DRIVE_REMOVABLE 3: DRIVE_FIXED 5: DRIVE_CDROM
88
+
89
+ if typeret == 2 || typeret == 3 || typeret == 5 {
90
+ lpVolumeNameBuffer := make([]byte, 256)
91
+ lpVolumeSerialNumber := int64(0)
92
+ lpMaximumComponentLength := int64(0)
93
+ lpFileSystemFlags := int64(0)
94
+ lpFileSystemNameBuffer := make([]byte, 256)
95
+ volpath, _ := syscall.UTF16PtrFromString(string(v) + ":/")
96
+ driveret, _, err := provGetVolumeInformation.Call(
97
+ uintptr(unsafe.Pointer(volpath)),
98
+ uintptr(unsafe.Pointer(&lpVolumeNameBuffer[0])),
99
+ uintptr(len(lpVolumeNameBuffer)),
100
+ uintptr(unsafe.Pointer(&lpVolumeSerialNumber)),
101
+ uintptr(unsafe.Pointer(&lpMaximumComponentLength)),
102
+ uintptr(unsafe.Pointer(&lpFileSystemFlags)),
103
+ uintptr(unsafe.Pointer(&lpFileSystemNameBuffer[0])),
104
+ uintptr(len(lpFileSystemNameBuffer)))
105
+ if driveret == 0 {
106
+ if typeret == 5 {
107
+ continue //device is not ready will happen if there is no disk in the drive
108
+ }
109
+ return ret, err
110
+ }
111
+ opts := "rw"
112
+ if lpFileSystemFlags&FileReadOnlyVolume != 0 {
113
+ opts = "ro"
114
+ }
115
+ if lpFileSystemFlags&FileFileCompression != 0 {
116
+ opts += ".compress"
117
+ }
118
+
119
+ d := DiskPartitionStat{
120
+ Mountpoint: path,
121
+ Device: path,
122
+ Fstype: string(bytes.Replace(lpFileSystemNameBuffer, []byte("\x00"), []byte(""), -1)),
123
+ Opts: opts,
124
+ }
125
+ ret = append(ret, d)
126
+ }
127
+ }
128
+ }
129
+ return ret, nil
130
+}
131
+
132
+func DiskIOCounters() (map[string]DiskIOCountersStat, error) {
133
+ ret := make(map[string]DiskIOCountersStat, 0)
134
+ var dst []Win32_PerfFormattedData
135
+
136
+ err := wmi.Query("SELECT * FROM Win32_PerfFormattedData_PerfDisk_LogicalDisk ", &dst)
137
+ if err != nil {
138
+ return ret, err
139
+ }
140
+ for _, d := range dst {
141
+ if len(d.Name) > 3 { // not get _Total or Harddrive
142
+ continue
143
+ }
144
+ ret[d.Name] = DiskIOCountersStat{
145
+ Name: d.Name,
146
+ ReadCount: uint64(d.AvgDiskReadQueueLength),
147
+ WriteCount: d.AvgDiskWriteQueueLength,
148
+ ReadBytes: uint64(d.AvgDiskBytesPerRead),
149
+ WriteBytes: uint64(d.AvgDiskBytesPerWrite),
150
+ ReadTime: d.AvgDisksecPerRead,
151
+ WriteTime: d.AvgDisksecPerWrite,
152
+ }
153
+ }
154
+ return ret, nil
155
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/disk/types_freebsd.go
new
+85
@@ -0,0 +1,85 @@
1
+// +build ignore
2
+// Hand writing: _Ctype_struct___0
3
+
4
+/*
5
+Input to cgo -godefs.
6
+
7
+*/
8
+
9
+package disk
10
+
11
+/*
12
+#include <sys/types.h>
13
+#include <sys/mount.h>
14
+#include <devstat.h>
15
+
16
+enum {
17
+ sizeofPtr = sizeof(void*),
18
+};
19
+
20
+// because statinfo has long double snap_time, redefine with changing long long
21
+struct statinfo2 {
22
+ long cp_time[CPUSTATES];
23
+ long tk_nin;
24
+ long tk_nout;
25
+ struct devinfo *dinfo;
26
+ long long snap_time;
27
+};
28
+*/
29
+import "C"
30
+
31
+// Machine characteristics; for internal use.
32
+
33
+const (
34
+ sizeofPtr = C.sizeofPtr
35
+ sizeofShort = C.sizeof_short
36
+ sizeofInt = C.sizeof_int
37
+ sizeofLong = C.sizeof_long
38
+ sizeofLongLong = C.sizeof_longlong
39
+ sizeofLongDouble = C.sizeof_longlong
40
+
41
+ DEVSTAT_NO_DATA = 0x00
42
+ DEVSTAT_READ = 0x01
43
+ DEVSTAT_WRITE = 0x02
44
+ DEVSTAT_FREE = 0x03
45
+
46
+ // from sys/mount.h
47
+ MNT_RDONLY = 0x00000001 /* read only filesystem */
48
+ MNT_SYNCHRONOUS = 0x00000002 /* filesystem written synchronously */
49
+ MNT_NOEXEC = 0x00000004 /* can't exec from filesystem */
50
+ MNT_NOSUID = 0x00000008 /* don't honor setuid bits on fs */
51
+ MNT_UNION = 0x00000020 /* union with underlying filesystem */
52
+ MNT_ASYNC = 0x00000040 /* filesystem written asynchronously */
53
+ MNT_SUIDDIR = 0x00100000 /* special handling of SUID on dirs */
54
+ MNT_SOFTDEP = 0x00200000 /* soft updates being done */
55
+ MNT_NOSYMFOLLOW = 0x00400000 /* do not follow symlinks */
56
+ MNT_GJOURNAL = 0x02000000 /* GEOM journal support enabled */
57
+ MNT_MULTILABEL = 0x04000000 /* MAC support for individual objects */
58
+ MNT_ACLS = 0x08000000 /* ACL support enabled */
59
+ MNT_NOATIME = 0x10000000 /* disable update of file access time */
60
+ MNT_NOCLUSTERR = 0x40000000 /* disable cluster read */
61
+ MNT_NOCLUSTERW = 0x80000000 /* disable cluster write */
62
+ MNT_NFS4ACLS = 0x00000010
63
+
64
+ MNT_WAIT = 1 /* synchronously wait for I/O to complete */
65
+ MNT_NOWAIT = 2 /* start all I/O, but do not wait for it */
66
+ MNT_LAZY = 3 /* push data not written by filesystem syncer */
67
+ MNT_SUSPEND = 4 /* Suspend file system after sync */
68
+
69
+)
70
+
71
+// Basic types
72
+
73
+type (
74
+ _C_short C.short
75
+ _C_int C.int
76
+ _C_long C.long
77
+ _C_long_long C.longlong
78
+ _C_long_double C.longlong
79
+)
80
+
81
+type Statfs C.struct_statfs
82
+type Fsid C.struct_fsid
83
+
84
+type Devstat C.struct_devstat
85
+type Bintime C.struct_bintime
Godeps/_workspace/src/github.com/shirou/gopsutil/mem/mem.go
new
+38
@@ -0,0 +1,38 @@
1
+package mem
2
+
3
+import (
4
+ "encoding/json"
5
+)
6
+
7
+type VirtualMemoryStat struct {
8
+ Total uint64 `json:"total"`
9
+ Available uint64 `json:"available"`
10
+ Used uint64 `json:"used"`
11
+ UsedPercent float64 `json:"used_percent"`
12
+ Free uint64 `json:"free"`
13
+ Active uint64 `json:"active"`
14
+ Inactive uint64 `json:"inactive"`
15
+ Buffers uint64 `json:"buffers"`
16
+ Cached uint64 `json:"cached"`
17
+ Wired uint64 `json:"wired"`
18
+ Shared uint64 `json:"shared"`
19
+}
20
+
21
+type SwapMemoryStat struct {
22
+ Total uint64 `json:"total"`
23
+ Used uint64 `json:"used"`
24
+ Free uint64 `json:"free"`
25
+ UsedPercent float64 `json:"used_percent"`
26
+ Sin uint64 `json:"sin"`
27
+ Sout uint64 `json:"sout"`
28
+}
29
+
30
+func (m VirtualMemoryStat) String() string {
31
+ s, _ := json.Marshal(m)
32
+ return string(s)
33
+}
34
+
35
+func (m SwapMemoryStat) String() string {
36
+ s, _ := json.Marshal(m)
37
+ return string(s)
38
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/mem/mem_darwin.go
new
+153
@@ -0,0 +1,153 @@
1
+// +build darwin
2
+
3
+package mem
4
+
5
+import (
6
+ "os/exec"
7
+ "strconv"
8
+ "strings"
9
+
10
+ common "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/shirou/gopsutil/common"
11
+)
12
+
13
+func getPageSize() (uint64, error) {
14
+ out, err := exec.Command("pagesize").Output()
15
+ if err != nil {
16
+ return 0, err
17
+ }
18
+ o := strings.TrimSpace(string(out))
19
+ p, err := strconv.ParseUint(o, 10, 64)
20
+ if err != nil {
21
+ return 0, err
22
+ }
23
+ return p, nil
24
+}
25
+
26
+// Runs vm_stat and returns Free and inactive pages
27
+func getVmStat(pagesize uint64, vms *VirtualMemoryStat) error {
28
+ out, err := exec.Command("vm_stat").Output()
29
+ if err != nil {
30
+ return err
31
+ }
32
+ return parseVmStat(string(out), pagesize, vms)
33
+}
34
+
35
+func parseVmStat(out string, pagesize uint64, vms *VirtualMemoryStat) error {
36
+ var err error
37
+
38
+ lines := strings.Split(out, "\n")
39
+ for _, line := range lines {
40
+ fields := strings.Split(line, ":")
41
+ if len(fields) < 2 {
42
+ continue
43
+ }
44
+ key := strings.TrimSpace(fields[0])
45
+ value := strings.Trim(fields[1], " .")
46
+ switch key {
47
+ case "Pages free":
48
+ free, e := strconv.ParseUint(value, 10, 64)
49
+ if e != nil {
50
+ err = e
51
+ }
52
+ vms.Free = free * pagesize
53
+ case "Pages inactive":
54
+ inactive, e := strconv.ParseUint(value, 10, 64)
55
+ if e != nil {
56
+ err = e
57
+ }
58
+ vms.Cached += inactive * pagesize
59
+ vms.Inactive = inactive * pagesize
60
+ case "Pages active":
61
+ active, e := strconv.ParseUint(value, 10, 64)
62
+ if e != nil {
63
+ err = e
64
+ }
65
+ vms.Active = active * pagesize
66
+ case "Pages wired down":
67
+ wired, e := strconv.ParseUint(value, 10, 64)
68
+ if e != nil {
69
+ err = e
70
+ }
71
+ vms.Wired = wired * pagesize
72
+ case "Pages purgeable":
73
+ purgeable, e := strconv.ParseUint(value, 10, 64)
74
+ if e != nil {
75
+ err = e
76
+ }
77
+ vms.Cached += purgeable * pagesize
78
+ }
79
+ }
80
+ return err
81
+}
82
+
83
+// VirtualMemory returns VirtualmemoryStat.
84
+func VirtualMemory() (*VirtualMemoryStat, error) {
85
+ ret := &VirtualMemoryStat{}
86
+
87
+ p, err := getPageSize()
88
+ if err != nil {
89
+ return nil, err
90
+ }
91
+ t, err := common.DoSysctrl("hw.memsize")
92
+ if err != nil {
93
+ return nil, err
94
+ }
95
+ total, err := strconv.ParseUint(t[0], 10, 64)
96
+ if err != nil {
97
+ return nil, err
98
+ }
99
+ err = getVmStat(p, ret)
100
+ if err != nil {
101
+ return nil, err
102
+ }
103
+
104
+ ret.Available = ret.Free + ret.Cached
105
+ ret.Total = total
106
+
107
+ ret.Used = ret.Total - ret.Free
108
+ ret.UsedPercent = float64(ret.Total-ret.Available) / float64(ret.Total) * 100.0
109
+
110
+ return ret, nil
111
+}
112
+
113
+// SwapMemory returns swapinfo.
114
+func SwapMemory() (*SwapMemoryStat, error) {
115
+ var ret *SwapMemoryStat
116
+
117
+ swapUsage, err := common.DoSysctrl("vm.swapusage")
118
+ if err != nil {
119
+ return ret, err
120
+ }
121
+
122
+ total := strings.Replace(swapUsage[2], "M", "", 1)
123
+ used := strings.Replace(swapUsage[5], "M", "", 1)
124
+ free := strings.Replace(swapUsage[8], "M", "", 1)
125
+
126
+ total_v, err := strconv.ParseFloat(total, 64)
127
+ if err != nil {
128
+ return nil, err
129
+ }
130
+ used_v, err := strconv.ParseFloat(used, 64)
131
+ if err != nil {
132
+ return nil, err
133
+ }
134
+ free_v, err := strconv.ParseFloat(free, 64)
135
+ if err != nil {
136
+ return nil, err
137
+ }
138
+
139
+ u := float64(0)
140
+ if total_v != 0 {
141
+ u = ((total_v - free_v) / total_v) * 100.0
142
+ }
143
+
144
+ // vm.swapusage shows "M", multiply 1000
145
+ ret = &SwapMemoryStat{
146
+ Total: uint64(total_v * 1000),
147
+ Used: uint64(used_v * 1000),
148
+ Free: uint64(free_v * 1000),
149
+ UsedPercent: u,
150
+ }
151
+
152
+ return ret, nil
153
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/mem/mem_darwin_test.go
new
+67
@@ -0,0 +1,67 @@
1
+// +build darwin
2
+
3
+package mem
4
+
5
+import (
6
+ "testing"
7
+)
8
+
9
+var vm_stat_out = `
10
+Mach Virtual Memory Statistics: (page size of 4096 bytes)
11
+Pages free: 105885.
12
+Pages active: 725641.
13
+Pages inactive: 449242.
14
+Pages speculative: 6155.
15
+Pages throttled: 0.
16
+Pages wired down: 560835.
17
+Pages purgeable: 128967.
18
+"Translation faults": 622528839.
19
+Pages copy-on-write: 17697839.
20
+Pages zero filled: 311034413.
21
+Pages reactivated: 4705104.
22
+Pages purged: 5605610.
23
+File-backed pages: 349192.
24
+Anonymous pages: 831846.
25
+Pages stored in compressor: 876507.
26
+Pages occupied by compressor: 249167.
27
+Decompressions: 4555025.
28
+Compressions: 7524729.
29
+Pageins: 40532443.
30
+Pageouts: 126496.
31
+Swapins: 2988073.
32
+Swapouts: 3283599.
33
+`
34
+
35
+func TestParseVmStat(t *testing.T) {
36
+ ret := &VirtualMemoryStat{}
37
+ err := parseVmStat(vm_stat_out, 4096, ret)
38
+
39
+ if err != nil {
40
+ t.Errorf("Expected no error, got %s\n", err.Error())
41
+ }
42
+
43
+ if ret.Free != uint64(105885*4096) {
44
+ t.Errorf("Free pages, actual: %d, expected: %d", ret.Free,
45
+ 105885*4096)
46
+ }
47
+
48
+ if ret.Inactive != uint64(449242*4096) {
49
+ t.Errorf("Inactive pages, actual: %d, expected: %d", ret.Inactive,
50
+ 449242*4096)
51
+ }
52
+
53
+ if ret.Active != uint64(725641*4096) {
54
+ t.Errorf("Active pages, actual: %d, expected: %d", ret.Active,
55
+ 725641*4096)
56
+ }
57
+
58
+ if ret.Wired != uint64(560835*4096) {
59
+ t.Errorf("Wired pages, actual: %d, expected: %d", ret.Wired,
60
+ 560835*4096)
61
+ }
62
+
63
+ if ret.Cached != uint64(128967*4096+449242.*4096) {
64
+ t.Errorf("Cached pages, actual: %d, expected: %d", ret.Cached,
65
+ 128967*4096+449242.*4096)
66
+ }
67
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/mem/mem_freebsd.go
new
+129
@@ -0,0 +1,129 @@
1
+// +build freebsd
2
+
3
+package mem
4
+
5
+import (
6
+ "os/exec"
7
+ "strconv"
8
+ "strings"
9
+
10
+ common "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/shirou/gopsutil/common"
11
+)
12
+
13
+func VirtualMemory() (*VirtualMemoryStat, error) {
14
+ pageSize, err := common.DoSysctrl("vm.stats.vm.v_page_size")
15
+ if err != nil {
16
+ return nil, err
17
+ }
18
+ p, err := strconv.ParseUint(pageSize[0], 10, 64)
19
+ if err != nil {
20
+ return nil, err
21
+ }
22
+
23
+ pageCount, err := common.DoSysctrl("vm.stats.vm.v_page_count")
24
+ if err != nil {
25
+ return nil, err
26
+ }
27
+ free, err := common.DoSysctrl("vm.stats.vm.v_free_count")
28
+ if err != nil {
29
+ return nil, err
30
+ }
31
+ active, err := common.DoSysctrl("vm.stats.vm.v_active_count")
32
+ if err != nil {
33
+ return nil, err
34
+ }
35
+ inactive, err := common.DoSysctrl("vm.stats.vm.v_inactive_count")
36
+ if err != nil {
37
+ return nil, err
38
+ }
39
+ cache, err := common.DoSysctrl("vm.stats.vm.v_cache_count")
40
+ if err != nil {
41
+ return nil, err
42
+ }
43
+ buffer, err := common.DoSysctrl("vfs.bufspace")
44
+ if err != nil {
45
+ return nil, err
46
+ }
47
+ wired, err := common.DoSysctrl("vm.stats.vm.v_wire_count")
48
+ if err != nil {
49
+ return nil, err
50
+ }
51
+
52
+ parsed := make([]uint64, 0, 7)
53
+ vv := []string{
54
+ pageCount[0],
55
+ free[0],
56
+ active[0],
57
+ inactive[0],
58
+ cache[0],
59
+ buffer[0],
60
+ wired[0],
61
+ }
62
+ for _, target := range vv {
63
+ t, err := strconv.ParseUint(target, 10, 64)
64
+ if err != nil {
65
+ return nil, err
66
+ }
67
+ parsed = append(parsed, t)
68
+ }
69
+
70
+ ret := &VirtualMemoryStat{
71
+ Total: parsed[0] * p,
72
+ Free: parsed[1] * p,
73
+ Active: parsed[2] * p,
74
+ Inactive: parsed[3] * p,
75
+ Cached: parsed[4] * p,
76
+ Buffers: parsed[5],
77
+ Wired: parsed[6] * p,
78
+ }
79
+
80
+ ret.Available = ret.Inactive + ret.Cached + ret.Free
81
+ ret.Used = ret.Active + ret.Wired + ret.Cached
82
+ ret.UsedPercent = float64(ret.Total-ret.Available) / float64(ret.Total) * 100.0
83
+
84
+ return ret, nil
85
+}
86
+
87
+// Return swapinfo
88
+// FreeBSD can have multiple swap devices. but use only first device
89
+func SwapMemory() (*SwapMemoryStat, error) {
90
+ out, err := exec.Command("swapinfo").Output()
91
+ if err != nil {
92
+ return nil, err
93
+ }
94
+ var ret *SwapMemoryStat
95
+ for _, line := range strings.Split(string(out), "\n") {
96
+ values := strings.Fields(line)
97
+ // skip title line
98
+ if len(values) == 0 || values[0] == "Device" {
99
+ continue
100
+ }
101
+
102
+ u := strings.Replace(values[4], "%", "", 1)
103
+ total_v, err := strconv.ParseUint(values[1], 10, 64)
104
+ if err != nil {
105
+ return nil, err
106
+ }
107
+ used_v, err := strconv.ParseUint(values[2], 10, 64)
108
+ if err != nil {
109
+ return nil, err
110
+ }
111
+ free_v, err := strconv.ParseUint(values[3], 10, 64)
112
+ if err != nil {
113
+ return nil, err
114
+ }
115
+ up_v, err := strconv.ParseFloat(u, 64)
116
+ if err != nil {
117
+ return nil, err
118
+ }
119
+
120
+ ret = &SwapMemoryStat{
121
+ Total: total_v,
122
+ Used: used_v,
123
+ Free: free_v,
124
+ UsedPercent: up_v,
125
+ }
126
+ }
127
+
128
+ return ret, nil
129
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/mem/mem_linux.go
new
+99
@@ -0,0 +1,99 @@
1
+// +build linux
2
+
3
+package mem
4
+
5
+import (
6
+ "strconv"
7
+ "strings"
8
+ "syscall"
9
+
10
+ common "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/shirou/gopsutil/common"
11
+)
12
+
13
+func VirtualMemory() (*VirtualMemoryStat, error) {
14
+ filename := "/proc/meminfo"
15
+ lines, _ := common.ReadLines(filename)
16
+ // flag if MemAvailable is in /proc/meminfo (kernel 3.14+)
17
+ memavail := false
18
+
19
+ ret := &VirtualMemoryStat{}
20
+ for _, line := range lines {
21
+ fields := strings.Split(line, ":")
22
+ if len(fields) != 2 {
23
+ continue
24
+ }
25
+ key := strings.TrimSpace(fields[0])
26
+ value := strings.TrimSpace(fields[1])
27
+ value = strings.Replace(value, " kB", "", -1)
28
+
29
+ t, err := strconv.ParseUint(value, 10, 64)
30
+ if err != nil {
31
+ return ret, err
32
+ }
33
+ switch key {
34
+ case "MemTotal":
35
+ ret.Total = t * 1024
36
+ case "MemFree":
37
+ ret.Free = t * 1024
38
+ case "MemAvailable":
39
+ memavail = true
40
+ ret.Available = t * 1024
41
+ case "Buffers":
42
+ ret.Buffers = t * 1024
43
+ case "Cached":
44
+ ret.Cached = t * 1024
45
+ case "Active":
46
+ ret.Active = t * 1024
47
+ case "Inactive":
48
+ ret.Inactive = t * 1024
49
+ }
50
+ }
51
+ if !memavail {
52
+ ret.Available = ret.Free + ret.Buffers + ret.Cached
53
+ }
54
+ ret.Used = ret.Total - ret.Free
55
+ ret.UsedPercent = float64(ret.Total-ret.Available) / float64(ret.Total) * 100.0
56
+
57
+ return ret, nil
58
+}
59
+
60
+func SwapMemory() (*SwapMemoryStat, error) {
61
+ sysinfo := &syscall.Sysinfo_t{}
62
+
63
+ if err := syscall.Sysinfo(sysinfo); err != nil {
64
+ return nil, err
65
+ }
66
+ ret := &SwapMemoryStat{
67
+ Total: uint64(sysinfo.Totalswap),
68
+ Free: uint64(sysinfo.Freeswap),
69
+ }
70
+ ret.Used = ret.Total - ret.Free
71
+ //check Infinity
72
+ if ret.Total != 0 {
73
+ ret.UsedPercent = float64(ret.Total-ret.Free) / float64(ret.Total) * 100.0
74
+ } else {
75
+ ret.UsedPercent = 0
76
+ }
77
+ lines, _ := common.ReadLines("/proc/vmstat")
78
+ for _, l := range lines {
79
+ fields := strings.Fields(l)
80
+ if len(fields) < 2 {
81
+ continue
82
+ }
83
+ switch fields[0] {
84
+ case "pswpin":
85
+ value, err := strconv.ParseUint(fields[1], 10, 64)
86
+ if err != nil {
87
+ continue
88
+ }
89
+ ret.Sin = value * 4 * 1024
90
+ case "pswpout":
91
+ value, err := strconv.ParseUint(fields[1], 10, 64)
92
+ if err != nil {
93
+ continue
94
+ }
95
+ ret.Sout = value * 4 * 1024
96
+ }
97
+ }
98
+ return ret, nil
99
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/mem/mem_test.go
new
+55
@@ -0,0 +1,55 @@
1
+package mem
2
+
3
+import (
4
+ "fmt"
5
+ "testing"
6
+)
7
+
8
+func TestVirtual_memory(t *testing.T) {
9
+ v, err := VirtualMemory()
10
+ if err != nil {
11
+ t.Errorf("error %v", err)
12
+ }
13
+ empty := &VirtualMemoryStat{}
14
+ if v == empty {
15
+ t.Errorf("error %v", v)
16
+ }
17
+}
18
+
19
+func TestSwap_memory(t *testing.T) {
20
+ v, err := SwapMemory()
21
+ if err != nil {
22
+ t.Errorf("error %v", err)
23
+ }
24
+ empty := &SwapMemoryStat{}
25
+ if v == empty {
26
+ t.Errorf("error %v", v)
27
+ }
28
+}
29
+
30
+func TestVirtualMemoryStat_String(t *testing.T) {
31
+ v := VirtualMemoryStat{
32
+ Total: 10,
33
+ Available: 20,
34
+ Used: 30,
35
+ UsedPercent: 30.1,
36
+ Free: 40,
37
+ }
38
+ e := `{"total":10,"available":20,"used":30,"used_percent":30.1,"free":40,"active":0,"inactive":0,"buffers":0,"cached":0,"wired":0,"shared":0}`
39
+ if e != fmt.Sprintf("%v", v) {
40
+ t.Errorf("VirtualMemoryStat string is invalid: %v", v)
41
+ }
42
+}
43
+
44
+func TestSwapMemoryStat_String(t *testing.T) {
45
+ v := SwapMemoryStat{
46
+ Total: 10,
47
+ Used: 30,
48
+ Free: 40,
49
+ UsedPercent: 30.1,
50
+ }
51
+ e := `{"total":10,"used":30,"free":40,"used_percent":30.1,"sin":0,"sout":0}`
52
+ if e != fmt.Sprintf("%v", v) {
53
+ t.Errorf("SwapMemoryStat string is invalid: %v", v)
54
+ }
55
+}
Godeps/_workspace/src/github.com/shirou/gopsutil/mem/mem_windows.go
new
+50
@@ -0,0 +1,50 @@
1
+// +build windows
2
+
3
+package mem
4
+
5
+import (
6
+ "syscall"
7
+ "unsafe"
8
+
9
+ common "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/shirou/gopsutil/common"
10
+)
11
+
12
+var (
13
+ procGlobalMemoryStatusEx = common.Modkernel32.NewProc("GlobalMemoryStatusEx")
14
+)
15
+
16
+type MEMORYSTATUSEX struct {
17
+ cbSize uint32
18
+ dwMemoryLoad uint32
19
+ ullTotalPhys uint64 // in bytes
20
+ ullAvailPhys uint64
21
+ ullTotalPageFile uint64
22
+ ullAvailPageFile uint64
23
+ ullTotalVirtual uint64
24
+ ullAvailVirtual uint64
25
+ ullAvailExtendedVirtual uint64
26
+}
27
+
28
+func VirtualMemory() (*VirtualMemoryStat, error) {
29
+ var memInfo MEMORYSTATUSEX
30
+ memInfo.cbSize = uint32(unsafe.Sizeof(memInfo))
31
+ mem, _, _ := procGlobalMemoryStatusEx.Call(uintptr(unsafe.Pointer(&memInfo)))
32
+ if mem == 0 {
33
+ return nil, syscall.GetLastError()
34
+ }
35
+
36
+ ret := &VirtualMemoryStat{
37
+ Total: memInfo.ullTotalPhys,
38
+ Available: memInfo.ullAvailPhys,
39
+ UsedPercent: float64(memInfo.dwMemoryLoad),
40
+ }
41
+
42
+ ret.Used = ret.Total - ret.Available
43
+ return ret, nil
44
+}
45
+
46
+func SwapMemory() (*SwapMemoryStat, error) {
47
+ ret := &SwapMemoryStat{}
48
+
49
+ return ret, nil
50
+}
cmd/ipfs/ipfs.go
-1
@@ -103,7 +103,6 @@ var cmdDetailsMap = map[*cmds.Command]cmdDetails{
103
daemonCmd: {doesNotUseConfigAsInput: true, cannotRunOnDaemon: true},
104
commandsClientCmd: {doesNotUseRepo: true},
105
commands.CommandsDaemonCmd: {doesNotUseRepo: true},
106
- commands.DiagCmd: {cannotRunOnClient: true},
106
commands.VersionCmd: {doesNotUseConfigAsInput: true, doesNotUseRepo: true}, // must be permitted to run before init
107
commands.UpdateCmd: {preemptsAutoUpdate: true, cannotRunOnDaemon: true},
108
commands.UpdateCheckCmd: {preemptsAutoUpdate: true},
core/commands/diag.go
+1
@@ -46,6 +46,7 @@ var DiagCmd = &cmds.Command{
46
47
Subcommands: map[string]*cmds.Command{
48
"net": diagNetCmd,
49
+ "sys": sysDiagCmd,
50
},
51
}
52
core/commands/sysdiag.go
new
+138
@@ -0,0 +1,138 @@
1
+package commands
2
+
3
+import (
4
+ "os"
5
+ "path"
6
+ "runtime"
7
+
8
+ cmds "github.com/ipfs/go-ipfs/commands"
9
+
10
+ manet "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/jbenet/go-multiaddr-net"
11
+ psud "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/shirou/gopsutil/disk"
12
+ psum "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/shirou/gopsutil/mem"
13
+)
14
+
15
+var sysDiagCmd = &cmds.Command{
16
+ Helptext: cmds.HelpText{
17
+ Tagline: "prints out system diagnostic information.",
18
+ ShortDescription: `
19
+Prints out information about your computer to aid in easier debugging.
20
+`,
21
+ },
22
+ Run: func(req cmds.Request, res cmds.Response) {
23
+ info := make(map[string]interface{})
24
+ err := runtimeInfo(info)
25
+ if err != nil {
26
+ res.SetError(err, cmds.ErrNormal)
27
+ return
28
+ }
29
+
30
+ err = envVarInfo(info)
31
+ if err != nil {
32
+ res.SetError(err, cmds.ErrNormal)
33
+ return
34
+ }
35
+
36
+ err = diskSpaceInfo(info)
37
+ if err != nil {
38
+ res.SetError(err, cmds.ErrNormal)
39
+ return
40
+ }
41
+
42
+ err = memInfo(info)
43
+ if err != nil {
44
+ res.SetError(err, cmds.ErrNormal)
45
+ return
46
+ }
47
+
48
+ err = netInfo(info)
49
+ if err != nil {
50
+ res.SetError(err, cmds.ErrNormal)
51
+ return
52
+ }
53
+
54
+ res.SetOutput(info)
55
+ },
56
+}
57
+
58
+func runtimeInfo(out map[string]interface{}) error {
59
+ rt := make(map[string]interface{})
60
+ rt["os"] = runtime.GOOS
61
+ rt["arch"] = runtime.GOARCH
62
+ rt["compiler"] = runtime.Compiler
63
+ rt["version"] = runtime.Version()
64
+ rt["numcpu"] = runtime.NumCPU()
65
+ rt["gomaxprocs"] = runtime.GOMAXPROCS(0)
66
+ rt["numgoroutines"] = runtime.NumGoroutine()
67
+
68
+ out["runtime"] = rt
69
+ return nil
70
+}
71
+
72
+func envVarInfo(out map[string]interface{}) error {
73
+ ev := make(map[string]interface{})
74
+ ev["GOPATH"] = os.Getenv("GOPATH")
75
+ ev["IPFS_PATH"] = os.Getenv("IPFS_PATH")
76
+
77
+ out["environment"] = ev
78
+ return nil
79
+}
80
+
81
+func ipfsPath() string {
82
+ p := os.Getenv("IPFS_PATH")
83
+ if p == "" {
84
+ p = path.Join(os.Getenv("HOME"), ".ipfs")
85
+ }
86
+ return p
87
+}
88
+
89
+func diskSpaceInfo(out map[string]interface{}) error {
90
+ di := make(map[string]interface{})
91
+ dinfo, err := psud.DiskUsage(ipfsPath())
92
+ if err != nil {
93
+ return err
94
+ }
95
+
96
+ di["fstype"] = dinfo.Fstype
97
+ di["total_space"] = dinfo.Total
98
+ di["used_space"] = dinfo.Used
99
+ di["free_space"] = dinfo.Free
100
+
101
+ out["diskinfo"] = di
102
+ return nil
103
+}
104
+
105
+func memInfo(out map[string]interface{}) error {
106
+ m := make(map[string]interface{})
107
+ swap, err := psum.SwapMemory()
108
+ if err != nil {
109
+ return err
110
+ }
111
+
112
+ virt, err := psum.VirtualMemory()
113
+ if err != nil {
114
+ return err
115
+ }
116
+
117
+ m["swap"] = swap
118
+ m["virt"] = virt
119
+ out["memory"] = m
120
+ return nil
121
+}
122
+
123
+func netInfo(out map[string]interface{}) error {
124
+ n := make(map[string]interface{})
125
+ addrs, err := manet.InterfaceMultiaddrs()
126
+ if err != nil {
127
+ return err
128
+ }
129
+
130
+ var straddrs []string
131
+ for _, a := range addrs {
132
+ straddrs = append(straddrs, a.String())
133
+ }
134
+
135
+ n["interface_addresses"] = straddrs
136
+ out["net"] = n
137
+ return nil
138
+}