go-proxy/job.go
Virgil 3376cea600 fix(pool): restore failover and stratum job handling
Co-Authored-By: Virgil <virgil@lethean.io>
2026-04-04 11:13:41 +00:00

72 lines
2.1 KiB
Go

package proxy
import (
"encoding/binary"
"encoding/hex"
"strconv"
)
// Job holds the current work unit received from a pool. Immutable once assigned.
//
// j := proxy.Job{
// Blob: "0707d5ef...b01",
// JobID: "4BiGm3/RgGQzgkTI",
// Target: "b88d0600",
// Algo: "cn/r",
// }
type Job struct {
Blob string `json:"blob"` // hex-encoded block template (160 hex chars = 80 bytes)
JobID string `json:"job_id"` // pool-assigned identifier
Target string `json:"target"` // 8-char hex little-endian uint32 difficulty target
Algo string `json:"algo"` // algorithm e.g. "cn/r", "rx/0"; "" if not negotiated
Height uint64 `json:"height"` // block height (0 if pool did not provide)
SeedHash string `json:"seed_hash"` // RandomX seed hash hex (empty if not RandomX)
ClientID string `json:"id"` // pool session ID that issued this job (for stale detection)
}
// IsValid returns true if Blob and JobID are non-empty.
//
// if !job.IsValid() { return }
func (j Job) IsValid() bool {
return j.Blob != "" && j.JobID != ""
}
// BlobWithFixedByte returns a copy of Blob with hex characters at positions 78-79
// (blob byte index 39) replaced by the two-digit lowercase hex of fixedByte.
//
// partitioned := job.BlobWithFixedByte(0x2A) // chars 78-79 become "2a"
func (j Job) BlobWithFixedByte(fixedByte uint8) string {
if len(j.Blob) < 80 {
return j.Blob
}
blob := []byte(j.Blob)
blob[78] = lowerHexDigit(fixedByte >> 4)
blob[79] = lowerHexDigit(fixedByte & 0x0F)
return string(blob)
}
// DifficultyFromTarget converts the 8-char little-endian hex Target field to a uint64 difficulty.
//
// diff := job.DifficultyFromTarget() // "b88d0600" → ~100000
func (j Job) DifficultyFromTarget() uint64 {
if len(j.Target) != 8 {
return 0
}
targetBytes, errorValue := hex.DecodeString(j.Target)
if errorValue != nil || len(targetBytes) != 4 {
return 0
}
targetValue := binary.LittleEndian.Uint32(targetBytes)
if targetValue == 0 {
return 0
}
return uint64(^uint32(0) / targetValue)
}
func lowerHexDigit(value uint8) byte {
return strconv.FormatUint(uint64(value), 16)[0]
}