sophuwu.site > quickstat
updating i guess
sophuwu sophie@skisiel.com
Thu, 11 Apr 2024 08:14:56 +0200
commit

8d50746b77be881b981ca446bb3e331f1723c487

parent

717415aa030f85dff15a76b0df4dd92c568e1f4b

3 files changed, 289 insertions(+), 162 deletions(-)

jump to
A cpu.go

@@ -0,0 +1,154 @@

+package main + +import ( + "encoding/json" + "fmt" + "os" + "time" +) + +type CPU struct { + Load float64 + MHz float64 + Temp int +} + +func (cpu *CPU) loadTemp() { + if cpu.Temp == -100 { + return + } + var findCPUTypeNo = func(path string, fileName string, comp string) (string, error) { + var b = make([]byte, 100) + var i int = 0 + if fileName == "_label" { + i = 1 + } + var err error = nil + for ; err == nil && string(b[:len(comp)]) != comp; i++ { + b, err = os.ReadFile(path + string(i+48) + fileName) + } + if err != nil { + return "", err + } + return string(i + 48 - 1), nil + } + Err := func(err error) bool { + if err == nil { + return false + } + cpu.Temp = -100 + return true + } + var ( + b = make([]byte, 2) + thrmPath = "/sys/class/thermal/thermal_zone" + hwMonPath = "/sys/class/hwmon/hwmon" + ) + nStr, err := findCPUTypeNo(thrmPath, "/type", "x86_pkg_temp") + if err != nil { + nStr, err = findCPUTypeNo(hwMonPath, "/name", "k10temp") + if Err(err) { + return + } + nStrHW := nStr + nStr, err = findCPUTypeNo(hwMonPath+nStrHW+"/temp", "_label", "Tdie") + if Err(err) { + return + } + b, err = os.ReadFile(hwMonPath + nStrHW + "/temp" + nStr + "_input") + } else { + b, err = os.ReadFile(thrmPath + nStr + "/temp") + } + if Err(err) { + return + } + cpu.Temp = (int(b[0])-48)*10 + int(b[1]) - 48 +} +func (c *CPU) loadMHz() { + b, err := os.ReadFile("/proc/cpuinfo") + + if errCheck(err, func() string { + cpuMHz = -1 + return "Unable to read cpu MHz.\n" + }) { + return + } + + var tmp, j int + c.MHz = 0 + for i := 0; i < len(b); i++ { + if string(b[i:i+7]) == "cpu MHz" { + tmp = 0 + for ; i < len(b) && b[i] != 10 && b[i] != '.'; i++ { + if b[i] >= 48 && b[i] <= 57 { + tmp = tmp*10 + int(b[i]) - 48 + } + } + cpuMHz += tmp + j++ + } + } + c.MHz /= j +} +func (c *CPU) loadUsage() { + readStat := func(n *[4]float64) bool { + errFunc := func() string { + cpuLoad = -1 + return "Unable to read cpu load.\n" + } + + b := make([]byte, 100) + f, err := os.Open("/proc/stat") + if errCheck(err, errFunc) { + return true + } + _, err = f.Read(b) + if errCheck(err, errFunc) { + return true + } + f.Close() + for i, j := 6, 0; j < 4; i++ { + if b[i] >= 48 && b[i] <= 57 { + n[j] = n[j]*10 + float64(b[i]) - 48 + } else if b[i] == ' ' { + j++ + } + } + return false + } + var a, b [4]float64 + if readStat(&a) { + return + } + time.Sleep(CONFIG.Time) + if readStat(&b) { + return + } + c.Load = ((b[0] + b[1] + b[2]) - (a[0] + a[1] + a[2])) / ((b[0] + b[1] + b[2] + b[3]) - (a[0] + a[1] + a[2] + a[3])) +} +func (c *CPU) update() { + go c.loadMHz() + go c.loadTemp() + c.loadUsage() +} +func (c *CPU) GHz() float64 { + return c.MHz / 1000 +} +func (c *CPU) TempStr() string { + if c.Temp == -100 { + return "" + } + return fmt.Sprintf("%d °C", c.Temp) +} +func (c *CPU) String() string { + if CONFIG.Json { + b, _ := json.Marshal(c) + return string(b) + } + return fmt.Sprintf("%.1f %c %.2f GHz %s\n", c.Load*100, '%', c.GHz(), c.TempStr()) +} +func Cpu() CPU { + var cpu CPU + cpu.update() + return cpu +}
M main.gomain.go

@@ -1,189 +1,88 @@

package main import ( + "encoding/json" + "fmt" "os" + "strings" "time" ) -var ( - cpuLoad, - cpuMHz, - cpuTemp int - totalMem, - usedMem, - takenMem, - freeMem, - availMem, - prctMem, - prctBuff, - prctFree float64 -) +const SI = "%KMG" -func errCheck(err error, errFunc func() string) bool { - if err == nil { - return false - } - print(" An error occurred: " + errFunc()) - if len(os.Args) > 1 && os.Args[1] == "-d" { - print(err.Error() + "\n") +var CONFIG = struct { + Json bool + Repeat bool + Unit int + Time time.Duration +}{false, false, 2, time.Second} + +func Help() { + fmt.Printf("Usage: %s [options]\n", os.Args[0]) + fmt.Println("Options:") + fmt.Println(" -j Output in JSON format") + fmt.Println(" -r Repeat output") + fmt.Printf(" -[%s] Use unit\n", SI) + fmt.Println(" -t<n> Set sampling time to n seconds") + os.Exit(0) +} +func parseTime(s string) time.Duration { + var n int + for s = s[strings.Index(s, "t")+1:]; len(s) > 0 && s[0] >= '0' && s[0] <= '9'; s = s[1:] { + n = n*10 + int(s[0]) - '0' } - return true + return time.Duration(n) * time.Second } - -func numFromLine(i int, b []byte, n *float64) int { - for ; i < len(b); i++ { - if b[i] == 10 { - return i + 1 - } - if b[i] >= 48 && b[i] <= 57 { - *n = *n*10 + float64(b[i]) - 48 +func init() { + if len(os.Args) > 1 { + for _, arg := range os.Args[1:] { + if strings.Count(arg, "-") < 2 { + if strings.Contains(arg, "j") { + CONFIG.Json = true + } + if strings.Contains(arg, "r") { + CONFIG.Repeat = true + } + for i, c := range SI { + if strings.Contains(arg, string(c)) { + CONFIG.Unit = i + } + } + if strings.Contains(arg, "t") { + CONFIG.Time = parseTime(arg) + } + } else { + Help() + } } } - return i } -func getMem() { - errFunc := func() string { - prctMem = -1 - prctBuff = -1 - prctFree = -1 - return "Unable to read memory.\n" - } - - b := make([]byte, 84) - f, err := os.Open("/proc/meminfo") - if errCheck(err, errFunc) { - return - } - _, err = f.Read(b) - if errCheck(err, errFunc) { - return - } - f.Close() - - i := numFromLine(0, b, &totalMem) - totalMem /= 1000 - i = numFromLine(i, b, &freeMem) - freeMem /= 1000 - _ = numFromLine(i, b, &availMem) - availMem /= 1000 +type Bytes uint64 - usedMem = totalMem - freeMem - takenMem = totalMem - availMem - prctMem = takenMem * 100 / totalMem - prctBuff = (usedMem - takenMem) * 100 / totalMem - prctFree = freeMem * 100 / totalMem -} +func (b Bytes) String() string { + if CONFIG.Unit == 0 { -func findCPUTypeNo(path string, fileName string, comp string) (string, error) { - var b = make([]byte, 100) - var i int = 0 - if fileName == "_label" { - i = 1 - } - var err error = nil - for ; err == nil && string(b[:len(comp)]) != comp; i++ { - b, err = os.ReadFile(path + string(i+48) + fileName) } - if err != nil { - return "", err - } - return string(i + 48 - 1), nil } -func getCPUTemp() { - errFunc := func() string { - cpuTemp = -1 - return "Unable to read CPU temperature.\n" - } - var ( - b = make([]byte, 2) - thrmPath = "/sys/class/thermal/thermal_zone" - hwMonPath = "/sys/class/hwmon/hwmon" - ) - nStr, err := findCPUTypeNo(thrmPath, "/type", "x86_pkg_temp") - if err != nil { - nStr, err = findCPUTypeNo(hwMonPath, "/name", "k10temp") - if errCheck(err, errFunc) { - return - } - nStrHW := nStr - nStr, err = findCPUTypeNo(hwMonPath+nStrHW+"/temp", "_label", "Tdie") - if errCheck(err, errFunc) { - return - } - b, err = os.ReadFile(hwMonPath + nStrHW + "/temp" + nStr + "_input") - } else { - b, err = os.ReadFile(thrmPath + nStr + "/temp") - } - if errCheck(err, errFunc) { - return - } - cpuTemp = (int(b[0])-48)*10 + int(b[1]) - 48 +type NetInfo struct { + Tx Bytes + Rx Bytes } - -func getCPU() { - readStat := func(n *[4]float64) bool { - errFunc := func() string { - cpuLoad = -1 - return "Unable to read cpu load.\n" - } - - b := make([]byte, 100) - f, err := os.Open("/proc/stat") - if errCheck(err, errFunc) { - return true - } - _, err = f.Read(b) - if errCheck(err, errFunc) { - return true - } - f.Close() - for i, j := 6, 0; j < 4; i++ { - if b[i] >= 48 && b[i] <= 57 { - n[j] = n[j]*10 + float64(b[i]) - 48 - } else if b[i] == ' ' { - j++ - } - } - return false - } - var a, b [4]float64 - if readStat(&a) { - return - } - time.Sleep(1 * time.Second) - if readStat(&b) { - return - } - cpuLoad = int(100 * ((b[0] + b[1] + b[2]) - (a[0] + a[1] + a[2])) / ((b[0] + b[1] + b[2] + b[3]) - (a[0] + a[1] + a[2] + a[3]))) +type HWInfo struct { + CPU CPU + MEM MEMInfo + NET NetInfo } -func getMHz() { - b, err := os.ReadFile("/proc/cpuinfo") - - if errCheck(err, func() string { - cpuMHz = -1 - return "Unable to read cpu MHz.\n" - }) { - return +func (i *HWInfo) String() string { + if CONFIG.Json { + b, _ := json.Marshal(i) + return string(b) } + return fmt.Sprintf("%s %s %s\n", i.CPU, i.MEM, i.NET) - var tmp, j int - cpuMHz = 0 - for i := 0; i < len(b); i++ { - if string(b[i:i+7]) == "cpu MHz" { - tmp = 0 - for ; i < len(b) && b[i] != 10 && b[i] != '.'; i++ { - if b[i] >= 48 && b[i] <= 57 { - tmp = tmp*10 + int(b[i]) - 48 - } - } - cpuMHz += tmp - j++ - } - } - cpuMHz /= j } func round(f float64) string {
A mem.go

@@ -0,0 +1,74 @@

+package main + +import ( + "fmt" + "os" +) + +type MEM struct { + Total Bytes + Free Bytes + Avail Bytes + Buffer Bytes +} +type numSeeker struct { + i int + b []byte +} + +func (n *numSeeker) Init(b []byte) { + n.b = b + n.i = 0 +} +func (n *numSeeker) End() bool { + return n.i >= len(n.b) +} +func (n *numSeeker) Seek() { + n.i++ +} +func (n *numSeeker) GetByte() uint8 { + return uint8(n.b[n.i]) +} +func (n *numSeeker) IsNum() bool { + e := n.GetByte() + return e >= 48 && e <= 57 +} +func (n *numSeeker) SeekToNum() { + for n.Seek(); !n.End(); n.Seek() { + if n.IsNum() { + break + } + } +} +func (n *numSeeker) GetNum() uint64 { + var num uint64 = 0 + for n.SeekToNum(); !n.End(); n.Seek() { + if n.IsNum() { + num = num*uint64(10) + uint64(uint8(n.GetByte())-48) + } else { + return num + } + } + return num +} +func (n *numSeeker) GetNums() []uint64 { + nums := make([]uint64, 0) + for ; !n.End(); n.Seek() { + nums = append(nums, n.GetNum()) + } + return nums +} + +func (m *MEM) update() { + + b := make([]byte, 140) + f, _ := os.Open("/proc/meminfo") + _, err := f.Read(b) + if err != nil { + return + } + f.Close() + var seeker numSeeker + seeker.Init(b) + fmt.Println(seeker.GetNums()) +}