Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/MHSanaei/3x-ui.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authormhsanaei <ho3ein.sanaei@gmail.com>2025-09-16 15:15:18 +0300
committermhsanaei <ho3ein.sanaei@gmail.com>2025-09-16 15:15:18 +0300
commitecfffa882a159bb2a12954eed0f68eb4ec1a6120 (patch)
tree18b34d40f61fa6b4103fd663e6c7b1f8a614a487 /util/sys/sys_darwin.go
parent3af5026abe639e9cb5a9f695c02624ac6e173077 (diff)
CPU History, CPU Utilization
Diffstat (limited to 'util/sys/sys_darwin.go')
-rw-r--r--util/sys/sys_darwin.go71
1 files changed, 71 insertions, 0 deletions
diff --git a/util/sys/sys_darwin.go b/util/sys/sys_darwin.go
index 3f5b2072..6ecc78c0 100644
--- a/util/sys/sys_darwin.go
+++ b/util/sys/sys_darwin.go
@@ -4,7 +4,12 @@
package sys
import (
+ "encoding/binary"
+ "fmt"
+ "sync"
+
"github.com/shirou/gopsutil/v4/net"
+ "golang.org/x/sys/unix"
)
func GetTCPCount() (int, error) {
@@ -22,3 +27,69 @@ func GetUDPCount() (int, error) {
}
return len(stats), nil
}
+
+// --- CPU Utilization (macOS native) ---
+
+// sysctl kern.cp_time returns an array of 5 longs: user, nice, sys, idle, intr.
+// We compute utilization deltas without cgo.
+var (
+ cpuMu sync.Mutex
+ lastTotals [5]uint64
+ hasLastCPUT bool
+)
+
+func CPUPercentRaw() (float64, error) {
+ raw, err := unix.SysctlRaw("kern.cp_time")
+ if err != nil {
+ return 0, err
+ }
+ // Expect either 5*8 bytes (uint64) or 5*4 bytes (uint32)
+ var out [5]uint64
+ switch len(raw) {
+ case 5 * 8:
+ for i := 0; i < 5; i++ {
+ out[i] = binary.LittleEndian.Uint64(raw[i*8 : (i+1)*8])
+ }
+ case 5 * 4:
+ for i := 0; i < 5; i++ {
+ out[i] = uint64(binary.LittleEndian.Uint32(raw[i*4 : (i+1)*4]))
+ }
+ default:
+ return 0, fmt.Errorf("unexpected kern.cp_time size: %d", len(raw))
+ }
+
+ // user, nice, sys, idle, intr
+ user := out[0]
+ nice := out[1]
+ sysv := out[2]
+ idle := out[3]
+ intr := out[4]
+
+ cpuMu.Lock()
+ defer cpuMu.Unlock()
+
+ if !hasLastCPUT {
+ lastTotals = out
+ hasLastCPUT = true
+ return 0, nil
+ }
+
+ dUser := user - lastTotals[0]
+ dNice := nice - lastTotals[1]
+ dSys := sysv - lastTotals[2]
+ dIdle := idle - lastTotals[3]
+ dIntr := intr - lastTotals[4]
+
+ lastTotals = out
+
+ totald := dUser + dNice + dSys + dIdle + dIntr
+ if totald == 0 {
+ return 0, nil
+ }
+ busy := totald - dIdle
+ pct := float64(busy) / float64(totald) * 100.0
+ if pct > 100 {
+ pct = 100
+ }
+ return pct, nil
+}