cadvisor/fs/fs.go
Vishnu Kannan b9e70f0240 Filesystem stats are now per container. As of now, fs stats are reported only for the
root cgroup.
To make cadvisor detect all the disks, the rootfs of host needs to mounted
inside cadvisor.
2014-09-30 23:48:34 +00:00

76 lines
1.8 KiB
Go

// +build linux
//
// Provides Filesystem Stats
package fs
/*
extern int getBytesFree(const char *path, unsigned long long *bytes);
extern int getBytesTotal(const char *path, unsigned long long *bytes);
*/
import "C"
import (
"strings"
"syscall"
"unsafe"
"github.com/docker/docker/pkg/mount"
"github.com/golang/glog"
)
type FsInfoImpl struct{}
func NewFsInfo() FsInfo {
return &FsInfoImpl{}
}
func (*FsInfoImpl) GetFsStats() ([]FsStat, error) {
filesystems := make([]FsStat, 0)
mounts, err := mount.GetMounts()
if err != nil {
return nil, err
}
processedPartitions := make(map[string]bool, 0)
for _, mount := range mounts {
if !strings.HasPrefix(mount.Fstype, "ext") {
continue
}
// Avoid bind mounts.
if _, ok := processedPartitions[mount.Source]; ok {
continue
}
total, free, err := getVfsStats(mount.Mountpoint)
if err != nil {
glog.Errorf("Statvfs failed. Error: %v", err)
} else {
glog.V(1).Infof("%s is an %s partition at %s. Total: %d, Free: %d", mount.Source, mount.Fstype, mount.Mountpoint, total, free)
fsStat := FsStat{
Device: mount.Source,
Major: uint(mount.Major),
Minor: uint(mount.Minor),
Capacity: total,
Free: free,
}
filesystems = append(filesystems, fsStat)
processedPartitions[mount.Source] = true
}
}
return filesystems, nil
}
func getVfsStats(path string) (total uint64, free uint64, err error) {
_p0, err := syscall.BytePtrFromString(path)
if err != nil {
return 0, 0, err
}
res, err := C.getBytesFree((*C.char)(unsafe.Pointer(_p0)), (*_Ctype_ulonglong)(unsafe.Pointer(&free)))
if res != 0 {
return 0, 0, err
}
res, err = C.getBytesTotal((*C.char)(unsafe.Pointer(_p0)), (*_Ctype_ulonglong)(unsafe.Pointer(&total)))
if res != 0 {
return 0, 0, err
}
return total, free, nil
}