Builder and Settings expose install base/subfolder with live preview. Agent embeds on first exe run to the configured path, pauses for idle CPU and scheduled windows, and reports real system CPU usage.
81 lines
1.7 KiB
Go
81 lines
1.7 KiB
Go
package stats
|
|
|
|
import (
|
|
"os"
|
|
"runtime"
|
|
"sync"
|
|
"syscall"
|
|
"unsafe"
|
|
)
|
|
|
|
type memoryStatusEx struct {
|
|
Length uint32
|
|
MemoryLoad uint32
|
|
TotalPhys uint64
|
|
AvailPhys uint64
|
|
TotalPageFile uint64
|
|
AvailPageFile uint64
|
|
TotalVirtual uint64
|
|
AvailVirtual uint64
|
|
AvailExtendedVirtual uint64
|
|
}
|
|
|
|
var (
|
|
kernel32 = syscall.NewLazyDLL("kernel32.dll")
|
|
procGlobalMemoryStatusEx = kernel32.NewProc("GlobalMemoryStatusEx")
|
|
)
|
|
|
|
type Reporter struct {
|
|
mu sync.Mutex
|
|
|
|
lastIdle uint64
|
|
lastKernel uint64
|
|
lastUser uint64
|
|
hasSample bool
|
|
}
|
|
|
|
func NewReporter() *Reporter {
|
|
return &Reporter{}
|
|
}
|
|
|
|
func (r *Reporter) SystemInfo() (hostname string, cpuCores int, memoryGB int) {
|
|
hostname, _ = os.Hostname()
|
|
cpuCores = runtime.NumCPU()
|
|
total, _ := r.memoryStatus()
|
|
memoryGB = int(total / (1024 * 1024 * 1024))
|
|
if memoryGB < 1 {
|
|
memoryGB = 1
|
|
}
|
|
return hostname, cpuCores, memoryGB
|
|
}
|
|
|
|
func (r *Reporter) Usage() (cpuPct float64, memPct float64) {
|
|
total, avail := r.memoryStatus()
|
|
if total > 0 {
|
|
memPct = float64(total-avail) / float64(total) * 100
|
|
}
|
|
// CPU usage is reported by the agent client from mining load; keep a sane default here.
|
|
cpuPct = 0
|
|
return cpuPct, memPct
|
|
}
|
|
|
|
func (r *Reporter) FreeMemoryMB() uint64 {
|
|
_, avail := r.memoryStatus()
|
|
return avail / (1024 * 1024)
|
|
}
|
|
|
|
func (r *Reporter) TotalMemoryMB() uint64 {
|
|
total, _ := r.memoryStatus()
|
|
return total / (1024 * 1024)
|
|
}
|
|
|
|
func (r *Reporter) memoryStatus() (total, avail uint64) {
|
|
var stat memoryStatusEx
|
|
stat.Length = uint32(unsafe.Sizeof(stat))
|
|
ret, _, _ := procGlobalMemoryStatusEx.Call(uintptr(unsafe.Pointer(&stat)))
|
|
if ret == 0 {
|
|
return 0, 0
|
|
}
|
|
return stat.TotalPhys, stat.AvailPhys
|
|
}
|