From 06e31e9b04c14e8c58f0dc5f183d2133fd1f5a3b Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:10:20 +0200 Subject: [PATCH 01/23] Add guest-aware runtime CPU limit discovery --- internal/hostlimits/limits.go | 264 ++++++++++++++++++++++++++++++++++ 1 file changed, 264 insertions(+) create mode 100644 internal/hostlimits/limits.go diff --git a/internal/hostlimits/limits.go b/internal/hostlimits/limits.go new file mode 100644 index 0000000..2727dc3 --- /dev/null +++ b/internal/hostlimits/limits.go @@ -0,0 +1,264 @@ +package hostlimits + +import ( + "bufio" + "fmt" + "os" + "runtime" + "sort" + "strconv" + "strings" + "time" +) + +const SchemaVersion = "quantum.runtime/host-limits/v1alpha1" + +type Limits struct { + SchemaVersion string `json:"schema_version"` + CollectedAt time.Time `json:"collected_at"` + EffectiveLogicalCPUs int `json:"effective_logical_cpus"` + AffinityCPUList string `json:"affinity_cpu_list,omitempty"` + AffinityLogicalCPUs int `json:"affinity_logical_cpus,omitempty"` + CgroupCPUSet string `json:"cgroup_cpuset,omitempty"` + CgroupCPUSetLogicalCPUs int `json:"cgroup_cpuset_logical_cpus,omitempty"` + CPUQuotaCores float64 `json:"cpu_quota_cores,omitempty"` + Virtualization Virtualization `json:"virtualization"` + Warnings []string `json:"warnings,omitempty"` +} + +type Virtualization struct { + Guest bool `json:"guest"` + Kind string `json:"kind"` + Evidence string `json:"evidence,omitempty"` +} + +func Discover() Limits { + limits := Limits{ + SchemaVersion: SchemaVersion, + CollectedAt: time.Now().UTC(), + EffectiveLogicalCPUs: runtime.NumCPU(), + Virtualization: discoverVirtualization(), + } + + if cpuList, err := processAffinityCPUList("/proc/self/status"); err == nil { + limits.AffinityCPUList = cpuList + if count, err := countCPUList(cpuList); err == nil { + limits.AffinityLogicalCPUs = count + limits.EffectiveLogicalCPUs = positiveMin(limits.EffectiveLogicalCPUs, count) + } else { + limits.Warnings = append(limits.Warnings, "affinity cpulist: "+err.Error()) + } + } else { + limits.Warnings = append(limits.Warnings, "process affinity: "+err.Error()) + } + + if cpuList, path, ok := discoverCgroupCPUSet(); ok { + limits.CgroupCPUSet = cpuList + if count, err := countCPUList(cpuList); err == nil { + limits.CgroupCPUSetLogicalCPUs = count + limits.EffectiveLogicalCPUs = positiveMin(limits.EffectiveLogicalCPUs, count) + } else { + limits.Warnings = append(limits.Warnings, path+": "+err.Error()) + } + } + + if quota, ok, err := discoverCPUQuota(); err != nil { + limits.Warnings = append(limits.Warnings, "cpu quota: "+err.Error()) + } else if ok { + limits.CPUQuotaCores = quota + } + + if limits.EffectiveLogicalCPUs < 1 { + limits.EffectiveLogicalCPUs = runtime.NumCPU() + } + return limits +} + +func (l Limits) Validate() error { + if l.SchemaVersion != SchemaVersion { + return fmt.Errorf("unexpected host limits schema %q", l.SchemaVersion) + } + if l.EffectiveLogicalCPUs < 1 { + return fmt.Errorf("effective logical CPU count must be positive") + } + if l.CPUQuotaCores < 0 { + return fmt.Errorf("cpu quota must not be negative") + } + return nil +} + +func processAffinityCPUList(path string) (string, error) { + f, err := os.Open(path) + if err != nil { + return "", err + } + defer f.Close() + + scanner := bufio.NewScanner(f) + for scanner.Scan() { + line := strings.TrimSpace(scanner.Text()) + if !strings.HasPrefix(line, "Cpus_allowed_list:") { + continue + } + value := strings.TrimSpace(strings.TrimPrefix(line, "Cpus_allowed_list:")) + if value == "" { + return "", fmt.Errorf("Cpus_allowed_list is empty") + } + return value, nil + } + if err := scanner.Err(); err != nil { + return "", err + } + return "", fmt.Errorf("Cpus_allowed_list not found") +} + +func discoverCgroupCPUSet() (string, string, bool) { + paths := []string{ + "/sys/fs/cgroup/cpuset.cpus.effective", + "/sys/fs/cgroup/cpuset.cpus", + "/sys/fs/cgroup/cpuset/cpuset.cpus", + } + for _, path := range paths { + data, err := os.ReadFile(path) + if err != nil { + continue + } + value := strings.TrimSpace(string(data)) + if value != "" { + return value, path, true + } + } + return "", "", false +} + +func discoverCPUQuota() (float64, bool, error) { + data, err := os.ReadFile("/sys/fs/cgroup/cpu.max") + if err == nil { + fields := strings.Fields(string(data)) + if len(fields) != 2 { + return 0, false, fmt.Errorf("invalid cpu.max") + } + if fields[0] == "max" { + return 0, false, nil + } + quota, err := strconv.ParseFloat(fields[0], 64) + if err != nil { + return 0, false, err + } + period, err := strconv.ParseFloat(fields[1], 64) + if err != nil || period <= 0 { + return 0, false, fmt.Errorf("invalid cpu.max period") + } + return quota / period, true, nil + } + + quotaData, quotaErr := os.ReadFile("/sys/fs/cgroup/cpu/cpu.cfs_quota_us") + periodData, periodErr := os.ReadFile("/sys/fs/cgroup/cpu/cpu.cfs_period_us") + if quotaErr != nil || periodErr != nil { + return 0, false, nil + } + quota, err := strconv.ParseFloat(strings.TrimSpace(string(quotaData)), 64) + if err != nil { + return 0, false, err + } + if quota < 0 { + return 0, false, nil + } + period, err := strconv.ParseFloat(strings.TrimSpace(string(periodData)), 64) + if err != nil || period <= 0 { + return 0, false, fmt.Errorf("invalid cgroup v1 cpu period") + } + return quota / period, true, nil +} + +func discoverVirtualization() Virtualization { + type evidenceFile struct { + path string + label string + } + files := []evidenceFile{ + {path: "/sys/class/dmi/id/product_name", label: "dmi product"}, + {path: "/sys/class/dmi/id/sys_vendor", label: "dmi vendor"}, + {path: "/sys/hypervisor/type", label: "hypervisor"}, + } + for _, item := range files { + data, err := os.ReadFile(item.path) + if err != nil { + continue + } + value := strings.ToLower(strings.TrimSpace(string(data))) + if kind := virtualizationKind(value); kind != "" { + return Virtualization{Guest: true, Kind: kind, Evidence: item.label + ": " + strings.TrimSpace(string(data))} + } + } + + if data, err := os.ReadFile("/proc/cpuinfo"); err == nil && strings.Contains(strings.ToLower(string(data)), " hypervisor") { + return Virtualization{Guest: true, Kind: "unknown-hypervisor", Evidence: "cpu hypervisor flag"} + } + return Virtualization{Guest: false, Kind: "bare-metal-or-undetected"} +} + +func virtualizationKind(value string) string { + switch { + case strings.Contains(value, "kvm"), strings.Contains(value, "qemu"): + return "kvm" + case strings.Contains(value, "vmware"): + return "vmware" + case strings.Contains(value, "virtualbox"): + return "virtualbox" + case strings.Contains(value, "microsoft"), strings.Contains(value, "hyper-v"), strings.Contains(value, "virtual machine"): + return "hyper-v" + case strings.Contains(value, "xen"): + return "xen" + default: + return "" + } +} + +func countCPUList(value string) (int, error) { + set := map[int]struct{}{} + for _, part := range strings.Split(strings.TrimSpace(value), ",") { + part = strings.TrimSpace(part) + if part == "" { + continue + } + if strings.Contains(part, "-") { + bounds := strings.SplitN(part, "-", 2) + start, err := strconv.Atoi(strings.TrimSpace(bounds[0])) + if err != nil { + return 0, fmt.Errorf("invalid CPU range %q", part) + } + end, err := strconv.Atoi(strings.TrimSpace(bounds[1])) + if err != nil || end < start { + return 0, fmt.Errorf("invalid CPU range %q", part) + } + for cpu := start; cpu <= end; cpu++ { + set[cpu] = struct{}{} + } + continue + } + cpu, err := strconv.Atoi(part) + if err != nil || cpu < 0 { + return 0, fmt.Errorf("invalid CPU %q", part) + } + set[cpu] = struct{}{} + } + if len(set) == 0 { + return 0, fmt.Errorf("CPU list is empty") + } + return len(set), nil +} + +func positiveMin(values ...int) int { + filtered := make([]int, 0, len(values)) + for _, value := range values { + if value > 0 { + filtered = append(filtered, value) + } + } + if len(filtered) == 0 { + return 0 + } + sort.Ints(filtered) + return filtered[0] +} From 1fe6f366be96c921fd34c17fbdc34af36e7ecafa Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:10:27 +0200 Subject: [PATCH 02/23] Test host limit CPU list parsing --- internal/hostlimits/limits_test.go | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) create mode 100644 internal/hostlimits/limits_test.go diff --git a/internal/hostlimits/limits_test.go b/internal/hostlimits/limits_test.go new file mode 100644 index 0000000..f70c64f --- /dev/null +++ b/internal/hostlimits/limits_test.go @@ -0,0 +1,28 @@ +package hostlimits + +import "testing" + +func TestCountCPUList(t *testing.T) { + count, err := countCPUList("0-3,8,10-11") + if err != nil { + t.Fatal(err) + } + if count != 7 { + t.Fatalf("count = %d, want 7", count) + } +} + +func TestCountCPUListRejectsBrokenRange(t *testing.T) { + if _, err := countCPUList("4-2"); err == nil { + t.Fatal("expected invalid range error") + } +} + +func TestVirtualizationKind(t *testing.T) { + if got := virtualizationKind("QEMU Standard PC"); got != "kvm" { + t.Fatalf("kind = %q, want kvm", got) + } + if got := virtualizationKind("physical server"); got != "" { + t.Fatalf("kind = %q, want empty", got) + } +} From e1c1d80e103c63172df588c2a0dd490c261b352b Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:10:39 +0200 Subject: [PATCH 03/23] Add deployment profile contract --- internal/deploymentprofile/profile.go | 154 ++++++++++++++++++++++++++ 1 file changed, 154 insertions(+) create mode 100644 internal/deploymentprofile/profile.go diff --git a/internal/deploymentprofile/profile.go b/internal/deploymentprofile/profile.go new file mode 100644 index 0000000..7c4a634 --- /dev/null +++ b/internal/deploymentprofile/profile.go @@ -0,0 +1,154 @@ +package deploymentprofile + +import ( + "bytes" + "embed" + "encoding/json" + "fmt" + "io" + "io/fs" + "sort" + "strings" +) + +const SchemaVersion = "quantum.runtime/deployment-profile/v1alpha1" + +//go:embed data/*.json +var builtinFS embed.FS + +type Profile struct { + SchemaVersion string `json:"schema_version"` + ID string `json:"id"` + DisplayName string `json:"display_name"` + Tier string `json:"tier"` + Description string `json:"description"` + Hardware HardwareRequirements `json:"hardware"` + Model ModelRequirements `json:"model"` +} + +type HardwareRequirements struct { + Memory MemoryRequirements `json:"memory"` + CPU CPURequirements `json:"cpu"` + Accelerator AcceleratorRequirements `json:"accelerator"` +} + +type MemoryRequirements struct { + MinimumBytes uint64 `json:"minimum_bytes"` + ECCRequired bool `json:"ecc_required"` + PreferredClass string `json:"preferred_class,omitempty"` +} + +type CPURequirements struct { + MinimumPhysicalCores int `json:"minimum_physical_cores"` + ReferenceMinClockMHz int `json:"reference_min_clock_mhz,omitempty"` +} + +type AcceleratorRequirements struct { + Required bool `json:"required"` +} + +type ModelRequirements struct { + ArchitectureClass string `json:"architecture_class"` +} + +type Registry struct { + byID map[string]Profile + ordered []string +} + +func (p Profile) Validate() error { + if p.SchemaVersion != SchemaVersion { + return fmt.Errorf("schema_version must be %q", SchemaVersion) + } + if strings.TrimSpace(p.ID) == "" { + return fmt.Errorf("id is required") + } + if strings.TrimSpace(p.DisplayName) == "" { + return fmt.Errorf("display_name is required") + } + if p.Tier != "production" && p.Tier != "compatibility" && p.Tier != "experimental" { + return fmt.Errorf("unsupported tier %q", p.Tier) + } + if p.Hardware.Memory.MinimumBytes == 0 { + return fmt.Errorf("hardware.memory.minimum_bytes must be positive") + } + if p.Hardware.CPU.MinimumPhysicalCores < 1 { + return fmt.Errorf("hardware.cpu.minimum_physical_cores must be positive") + } + if p.Hardware.CPU.ReferenceMinClockMHz < 0 { + return fmt.Errorf("hardware.cpu.reference_min_clock_mhz must not be negative") + } + class := strings.ToLower(strings.TrimSpace(p.Model.ArchitectureClass)) + if class != "dense" && class != "moe" && class != "any" { + return fmt.Errorf("unsupported model architecture_class %q", p.Model.ArchitectureClass) + } + return nil +} + +func Builtin() (*Registry, error) { + entries, err := fs.ReadDir(builtinFS, "data") + if err != nil { + return nil, fmt.Errorf("read builtin deployment profiles: %w", err) + } + registry := &Registry{byID: map[string]Profile{}} + for _, entry := range entries { + if entry.IsDir() || !strings.HasSuffix(entry.Name(), ".json") { + continue + } + data, err := builtinFS.ReadFile("data/" + entry.Name()) + if err != nil { + return nil, fmt.Errorf("read deployment profile %s: %w", entry.Name(), err) + } + decoder := json.NewDecoder(bytes.NewReader(data)) + decoder.DisallowUnknownFields() + var profile Profile + if err := decoder.Decode(&profile); err != nil { + return nil, fmt.Errorf("decode deployment profile %s: %w", entry.Name(), err) + } + var trailing any + if err := decoder.Decode(&trailing); err != io.EOF { + if err == nil { + return nil, fmt.Errorf("deployment profile %s contains trailing JSON values", entry.Name()) + } + return nil, fmt.Errorf("decode trailing data in deployment profile %s: %w", entry.Name(), err) + } + if err := profile.Validate(); err != nil { + return nil, fmt.Errorf("deployment profile %s: %w", entry.Name(), err) + } + if _, exists := registry.byID[profile.ID]; exists { + return nil, fmt.Errorf("duplicate deployment profile %q", profile.ID) + } + registry.byID[profile.ID] = profile + registry.ordered = append(registry.ordered, profile.ID) + } + if len(registry.byID) == 0 { + return nil, fmt.Errorf("no builtin deployment profiles were found") + } + sort.Strings(registry.ordered) + return registry, nil +} + +func MustBuiltin() *Registry { + registry, err := Builtin() + if err != nil { + panic(fmt.Sprintf("invalid builtin deployment profiles: %v", err)) + } + return registry +} + +func (r *Registry) Lookup(id string) (Profile, bool) { + profile, ok := r.byID[strings.TrimSpace(id)] + return profile, ok +} + +func (r *Registry) List() []Profile { + profiles := make([]Profile, 0, len(r.ordered)) + for _, id := range r.ordered { + profiles = append(profiles, r.byID[id]) + } + return profiles +} + +func (r *Registry) Len() int { + return len(r.ordered) +} From b503115da2ab75fa1b1a6f1c2fe16a2d1673d6af Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:10:49 +0200 Subject: [PATCH 04/23] Add E.M.B.E.R. production deployment profile --- .../data/ember-production.json | 24 +++++++++++++++++++ 1 file changed, 24 insertions(+) create mode 100644 internal/deploymentprofile/data/ember-production.json diff --git a/internal/deploymentprofile/data/ember-production.json b/internal/deploymentprofile/data/ember-production.json new file mode 100644 index 0000000..10271c3 --- /dev/null +++ b/internal/deploymentprofile/data/ember-production.json @@ -0,0 +1,24 @@ +{ + "schema_version": "quantum.runtime/deployment-profile/v1alpha1", + "id": "ember-production", + "display_name": "E.M.B.E.R. Production", + "tier": "production", + "description": "Application-level E.M.B.E.R. production profile. This is not a generic Quantum Runtime minimum.", + "hardware": { + "memory": { + "minimum_bytes": 68719476736, + "ecc_required": true, + "preferred_class": "ddr5" + }, + "cpu": { + "minimum_physical_cores": 8, + "reference_min_clock_mhz": 2600 + }, + "accelerator": { + "required": false + } + }, + "model": { + "architecture_class": "moe" + } +} From fb8c4dac1eaaa43ef74ab346ac545525293459ff Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:10:57 +0200 Subject: [PATCH 05/23] Test E.M.B.E.R. deployment profile --- internal/deploymentprofile/profile_test.go | 29 ++++++++++++++++++++++ 1 file changed, 29 insertions(+) create mode 100644 internal/deploymentprofile/profile_test.go diff --git a/internal/deploymentprofile/profile_test.go b/internal/deploymentprofile/profile_test.go new file mode 100644 index 0000000..599a750 --- /dev/null +++ b/internal/deploymentprofile/profile_test.go @@ -0,0 +1,29 @@ +package deploymentprofile + +import "testing" + +func TestBuiltinEmberProduction(t *testing.T) { + registry, err := Builtin() + if err != nil { + t.Fatal(err) + } + profile, ok := registry.Lookup("ember-production") + if !ok { + t.Fatal("ember-production profile missing") + } + if profile.Hardware.Memory.MinimumBytes != 64<<30 { + t.Fatalf("memory minimum = %d", profile.Hardware.Memory.MinimumBytes) + } + if !profile.Hardware.Memory.ECCRequired { + t.Fatal("ECC must be required") + } + if profile.Hardware.CPU.MinimumPhysicalCores != 8 { + t.Fatalf("core minimum = %d", profile.Hardware.CPU.MinimumPhysicalCores) + } + if profile.Model.ArchitectureClass != "moe" { + t.Fatalf("architecture = %q", profile.Model.ArchitectureClass) + } + if profile.Hardware.Accelerator.Required { + t.Fatal("GPU must remain optional") + } +} From 5e31bd91906bbdd1fc640bcdc458291973b7a37f Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:11:23 +0200 Subject: [PATCH 06/23] Add application profile admission engine --- internal/admission/admission.go | 239 ++++++++++++++++++++++++++++++++ 1 file changed, 239 insertions(+) create mode 100644 internal/admission/admission.go diff --git a/internal/admission/admission.go b/internal/admission/admission.go new file mode 100644 index 0000000..03d1d33 --- /dev/null +++ b/internal/admission/admission.go @@ -0,0 +1,239 @@ +package admission + +import ( + "fmt" + "strings" + + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/deploymentprofile" + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/hostlimits" + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/hostprofile" + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/modelmanifest" +) + +const SchemaVersion = "quantum.runtime/admission-result/v1alpha1" + +const ( + DecisionAdmitted = "admitted" + DecisionRejected = "rejected" + DecisionNeedsOperatorEvidence = "needs_operator_evidence" +) + +type OperatorEvidence struct { + ECCVerified *bool `json:"ecc_verified,omitempty"` + MemoryClass string `json:"memory_class,omitempty"` + DedicatedPhysicalCores int `json:"dedicated_physical_cores,omitempty"` + CoreBudget int `json:"core_budget,omitempty"` +} + +type Check struct { + ID string `json:"id"` + Mandatory bool `json:"mandatory"` + State string `json:"state"` + Required any `json:"required,omitempty"` + Observed any `json:"observed,omitempty"` + Source string `json:"source,omitempty"` + Detail string `json:"detail,omitempty"` +} + +type Result struct { + SchemaVersion string `json:"schema_version"` + Decision string `json:"decision"` + ProfileID string `json:"profile_id"` + CanonicalModelID string `json:"canonical_model_id"` + Checks []Check `json:"checks"` +} + +func Evaluate(profile deploymentprofile.Profile, host hostprofile.Profile, limits hostlimits.Limits, model modelmanifest.Manifest, evidence OperatorEvidence) (Result, error) { + if err := profile.Validate(); err != nil { + return Result{}, fmt.Errorf("deployment profile: %w", err) + } + if err := host.Validate(); err != nil { + return Result{}, fmt.Errorf("host profile: %w", err) + } + if err := limits.Validate(); err != nil { + return Result{}, fmt.Errorf("host limits: %w", err) + } + if err := model.Validate(); err != nil { + return Result{}, fmt.Errorf("model manifest: %w", err) + } + if evidence.DedicatedPhysicalCores < 0 || evidence.CoreBudget < 0 { + return Result{}, fmt.Errorf("operator core evidence must not be negative") + } + + result := Result{ + SchemaVersion: SchemaVersion, + ProfileID: profile.ID, + CanonicalModelID: model.ID, + } + + requiredArchitecture := strings.ToLower(strings.TrimSpace(profile.Model.ArchitectureClass)) + observedArchitecture := strings.ToLower(strings.TrimSpace(model.Model.ArchitectureClass)) + architecturePass := requiredArchitecture == "any" || observedArchitecture == requiredArchitecture + result.Checks = append(result.Checks, booleanCheck( + "model.architecture_class", + true, + architecturePass, + requiredArchitecture, + observedArchitecture, + "model_manifest", + "The application profile is admitted by architecture capability, not by model-name matching.", + )) + + result.Checks = append(result.Checks, booleanCheck( + "hardware.memory.minimum_bytes", + true, + host.Memory.TotalBytes >= profile.Hardware.Memory.MinimumBytes, + profile.Hardware.Memory.MinimumBytes, + host.Memory.TotalBytes, + "host_profile", + "Installed/visible memory capacity is evaluated independently from current free-memory pressure.", + )) + + physicalCores := host.CPU.PhysicalCores + physicalSource := "host_topology" + if evidence.DedicatedPhysicalCores > 0 { + physicalCores = evidence.DedicatedPhysicalCores + physicalSource = "operator_evidence" + } + result.Checks = append(result.Checks, booleanCheck( + "hardware.cpu.minimum_physical_cores", + true, + physicalCores >= profile.Hardware.CPU.MinimumPhysicalCores, + profile.Hardware.CPU.MinimumPhysicalCores, + physicalCores, + physicalSource, + "On virtualized hosts, provider dedication cannot be inferred from the CPU model name; operator evidence may replace guest-topology evidence.", + )) + + effectiveBudget := limits.EffectiveLogicalCPUs + budgetSource := "process_affinity/cgroup" + if evidence.CoreBudget > 0 { + effectiveBudget = evidence.CoreBudget + budgetSource = "operator_core_budget" + } + budgetPass := effectiveBudget >= profile.Hardware.CPU.MinimumPhysicalCores && effectiveBudget <= limits.EffectiveLogicalCPUs + result.Checks = append(result.Checks, booleanCheck( + "hardware.cpu.runtime_budget", + true, + budgetPass, + map[string]any{"minimum": profile.Hardware.CPU.MinimumPhysicalCores, "maximum_visible": limits.EffectiveLogicalCPUs}, + effectiveBudget, + budgetSource, + "The Runtime budget prevents a profile from assuming all host-model cores are available to the guest or application.", + )) + + if profile.Hardware.Memory.ECCRequired { + check := Check{ + ID: "hardware.memory.ecc", + Mandatory: true, + Required: true, + Source: "operator_evidence", + Detail: "ECC is not guessed from ordinary guest userspace when trustworthy evidence is unavailable.", + } + if evidence.ECCVerified == nil { + check.State = "unknown" + check.Observed = "unknown" + } else { + check.Observed = *evidence.ECCVerified + if *evidence.ECCVerified { + check.State = "pass" + } else { + check.State = "fail" + } + } + result.Checks = append(result.Checks, check) + } + + if preferred := strings.ToLower(strings.TrimSpace(profile.Hardware.Memory.PreferredClass)); preferred != "" { + observed := strings.ToLower(strings.TrimSpace(evidence.MemoryClass)) + check := Check{ + ID: "hardware.memory.preferred_class", + Mandatory: false, + Required: preferred, + Source: "operator_evidence", + Detail: "Memory generation is a preference for this profile, not a generic Runtime hard gate.", + } + switch { + case observed == "": + check.State = "unknown" + check.Observed = "unknown" + case observed == preferred: + check.State = "pass" + check.Observed = observed + default: + check.State = "preference_miss" + check.Observed = observed + } + result.Checks = append(result.Checks, check) + } + + result.Checks = append(result.Checks, Check{ + ID: "hardware.accelerator.required", + Mandatory: profile.Hardware.Accelerator.Required, + State: acceleratorState(profile, host), + Required: profile.Hardware.Accelerator.Required, + Observed: len(host.Accelerators), + Source: "host_profile", + Detail: "CPU-only remains a first-class profile when an accelerator is not required.", + }) + + if profile.Hardware.CPU.ReferenceMinClockMHz > 0 { + result.Checks = append(result.Checks, Check{ + ID: "hardware.cpu.reference_clock_mhz", + Mandatory: false, + State: "advisory", + Required: profile.Hardware.CPU.ReferenceMinClockMHz, + Observed: "not_used_for_admission", + Source: "profile_reference", + Detail: "Raw clock frequency is historical/advisory only; calibrated throughput and topology take precedence.", + }) + } + + result.Decision = decide(result.Checks) + return result, nil +} + +func booleanCheck(id string, mandatory, pass bool, required, observed any, source, detail string) Check { + state := "fail" + if pass { + state = "pass" + } + return Check{ + ID: id, + Mandatory: mandatory, + State: state, + Required: required, + Observed: observed, + Source: source, + Detail: detail, + } +} + +func acceleratorState(profile deploymentprofile.Profile, host hostprofile.Profile) string { + if !profile.Hardware.Accelerator.Required { + return "pass" + } + if len(host.Accelerators) > 0 { + return "pass" + } + return "fail" +} + +func decide(checks []Check) string { + unknownMandatory := false + for _, check := range checks { + if !check.Mandatory { + continue + } + if check.State == "fail" { + return DecisionRejected + } + if check.State == "unknown" { + unknownMandatory = true + } + } + if unknownMandatory { + return DecisionNeedsOperatorEvidence + } + return DecisionAdmitted +} From 10197e1c34ed6f4134633c57c049e35914e578e7 Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:11:36 +0200 Subject: [PATCH 07/23] Test E.M.B.E.R. admission decisions --- internal/admission/admission_test.go | 122 +++++++++++++++++++++++++++ 1 file changed, 122 insertions(+) create mode 100644 internal/admission/admission_test.go diff --git a/internal/admission/admission_test.go b/internal/admission/admission_test.go new file mode 100644 index 0000000..79a5a59 --- /dev/null +++ b/internal/admission/admission_test.go @@ -0,0 +1,122 @@ +package admission + +import ( + "testing" + + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/deploymentprofile" + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/hostlimits" + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/hostprofile" + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/modelmanifest" +) + +func TestEmberProductionNeedsECCEvidence(t *testing.T) { + profile := emberProfile(t) + host := suitableHost() + limits := suitableLimits() + model := moeModel() + result, err := Evaluate(profile, host, limits, model, OperatorEvidence{}) + if err != nil { + t.Fatal(err) + } + if result.Decision != DecisionNeedsOperatorEvidence { + t.Fatalf("decision = %q", result.Decision) + } +} + +func TestEmberProductionAdmitsVerifiedCurrentClass(t *testing.T) { + profile := emberProfile(t) + host := suitableHost() + limits := suitableLimits() + model := moeModel() + ecc := true + result, err := Evaluate(profile, host, limits, model, OperatorEvidence{ + ECCVerified: &ecc, + MemoryClass: "ddr5", + DedicatedPhysicalCores: 20, + CoreBudget: 16, + }) + if err != nil { + t.Fatal(err) + } + if result.Decision != DecisionAdmitted { + t.Fatalf("decision = %q checks=%+v", result.Decision, result.Checks) + } +} + +func TestDenseModelCannotSatisfyMoEProfile(t *testing.T) { + profile := emberProfile(t) + host := suitableHost() + limits := suitableLimits() + model := moeModel() + model.Model.ArchitectureClass = "dense" + ecc := true + result, err := Evaluate(profile, host, limits, model, OperatorEvidence{ECCVerified: &ecc}) + if err != nil { + t.Fatal(err) + } + if result.Decision != DecisionRejected { + t.Fatalf("decision = %q", result.Decision) + } +} + +func TestOperatorCoreBudgetCanProtectSharedServices(t *testing.T) { + profile := emberProfile(t) + host := suitableHost() + limits := suitableLimits() + model := moeModel() + ecc := true + result, err := Evaluate(profile, host, limits, model, OperatorEvidence{ECCVerified: &ecc, CoreBudget: 4}) + if err != nil { + t.Fatal(err) + } + if result.Decision != DecisionRejected { + t.Fatalf("decision = %q", result.Decision) + } +} + +func emberProfile(t *testing.T) deploymentprofile.Profile { + t.Helper() + registry, err := deploymentprofile.Builtin() + if err != nil { + t.Fatal(err) + } + profile, ok := registry.Lookup("ember-production") + if !ok { + t.Fatal("ember-production missing") + } + return profile +} + +func suitableHost() hostprofile.Profile { + return hostprofile.Profile{ + SchemaVersion: hostprofile.SchemaVersion, + CPU: hostprofile.CPUProfile{PhysicalCores: 20, LogicalCores: 20, ThreadsPerCore: 1}, + Memory: hostprofile.MemoryProfile{TotalBytes: 96 << 30, AvailableBytes: 80 << 30}, + } +} + +func suitableLimits() hostlimits.Limits { + return hostlimits.Limits{SchemaVersion: hostlimits.SchemaVersion, EffectiveLogicalCPUs: 20} +} + +func moeModel() modelmanifest.Manifest { + return modelmanifest.Manifest{ + SchemaVersion: modelmanifest.SchemaVersion, + ID: "test-moe", + DisplayName: "Test MoE", + Source: modelmanifest.Source{Provider: "profile", Reference: "test/moe", Revision: "unresolved"}, + Backend: modelmanifest.Backend{Type: "external"}, + Artifacts: []modelmanifest.Artifact{{URI: "profile://test/moe"}}, + Model: modelmanifest.Model{ + Architecture: "test", + ArchitectureClass: "moe", + ParameterClass: "test", + Quantization: "q4", + ContextWindow: 8192, + }, + Capabilities: modelmanifest.Capabilities{Text: true}, + Compatibility: modelmanifest.Compatibility{MinRuntimeVersion: "0.3.0-alpha.1"}, + State: modelmanifest.State{Install: "available", Verification: "unverified", Lifecycle: "active"}, + Provenance: modelmanifest.Provenance{Publisher: "test"}, + } +} From 488030938ca62466b6c674dafcc11aa5eab4a3e7 Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:11:49 +0200 Subject: [PATCH 08/23] Add real-model CPU benchmark plan contract --- internal/benchmarkplan/plan.go | 95 ++++++++++++++++++++++++++++++++++ 1 file changed, 95 insertions(+) create mode 100644 internal/benchmarkplan/plan.go diff --git a/internal/benchmarkplan/plan.go b/internal/benchmarkplan/plan.go new file mode 100644 index 0000000..ce46dfa --- /dev/null +++ b/internal/benchmarkplan/plan.go @@ -0,0 +1,95 @@ +package benchmarkplan + +import ( + "fmt" + "sort" + + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/hostlimits" +) + +const SchemaVersion = "quantum.runtime/model-benchmark-plan/v1alpha1" + +type Request struct { + CoreBudget int `json:"core_budget,omitempty"` + ReserveSystemCores int `json:"reserve_system_cores,omitempty"` + MinimumWorkers int `json:"minimum_workers,omitempty"` + IncludeFullHostComparison bool `json:"include_full_host_comparison,omitempty"` +} + +type Candidate struct { + Workers int `json:"workers"` + Mode string `json:"mode"` +} + +type Plan struct { + SchemaVersion string `json:"schema_version"` + EffectiveHostCPUs int `json:"effective_host_cpus"` + ProductionMaxWorkers int `json:"production_max_workers"` + ReservedSystemCores int `json:"reserved_system_cores"` + Candidates []Candidate `json:"candidates"` + Notes []string `json:"notes,omitempty"` +} + +func Build(limits hostlimits.Limits, req Request) (Plan, error) { + if err := limits.Validate(); err != nil { + return Plan{}, err + } + if req.CoreBudget < 0 || req.ReserveSystemCores < 0 || req.MinimumWorkers < 0 { + return Plan{}, fmt.Errorf("benchmark core values must not be negative") + } + effective := limits.EffectiveLogicalCPUs + productionMax := effective - req.ReserveSystemCores + if productionMax < 1 { + return Plan{}, fmt.Errorf("system core reserve leaves no CPU capacity for benchmarking") + } + if req.CoreBudget > 0 { + if req.CoreBudget > effective { + return Plan{}, fmt.Errorf("core_budget exceeds effective host CPUs") + } + if req.CoreBudget < productionMax { + productionMax = req.CoreBudget + } + } + minimum := req.MinimumWorkers + if minimum == 0 { + minimum = 4 + } + if minimum > productionMax { + minimum = productionMax + } + + canonical := []int{1, 2, 4, 8, 12, 16, 20, 24, 32, 48, 64, 96, 128, 192} + set := map[int]string{} + for _, workers := range canonical { + if workers >= minimum && workers <= productionMax { + set[workers] = "production" + } + } + set[productionMax] = "production" + if req.IncludeFullHostComparison && effective > productionMax { + set[effective] = "full_host_comparison" + } + + workers := make([]int, 0, len(set)) + for value := range set { + workers = append(workers, value) + } + sort.Ints(workers) + candidates := make([]Candidate, 0, len(workers)) + for _, value := range workers { + candidates = append(candidates, Candidate{Workers: value, Mode: set[value]}) + } + + plan := Plan{ + SchemaVersion: SchemaVersion, + EffectiveHostCPUs: effective, + ProductionMaxWorkers: productionMax, + ReservedSystemCores: req.ReserveSystemCores, + Candidates: candidates, + Notes: []string{ + "This plan defines thread-count candidates only; it does not claim model throughput before measurement.", + "Prefill and decode must be recorded separately for each backend/model/quantization/context tuple.", + }, + } + return plan, nil +} From 112c9acf58ff0c221655aa70239a66c53f1dd8a2 Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:12:00 +0200 Subject: [PATCH 09/23] Test current 20-core Ember benchmark matrix --- internal/benchmarkplan/plan_test.go | 37 +++++++++++++++++++++++++++++ 1 file changed, 37 insertions(+) create mode 100644 internal/benchmarkplan/plan_test.go diff --git a/internal/benchmarkplan/plan_test.go b/internal/benchmarkplan/plan_test.go new file mode 100644 index 0000000..4306840 --- /dev/null +++ b/internal/benchmarkplan/plan_test.go @@ -0,0 +1,37 @@ +package benchmarkplan + +import ( + "reflect" + "testing" + + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/hostlimits" +) + +func TestCurrentTwentyCoreHostPlan(t *testing.T) { + limits := hostlimits.Limits{SchemaVersion: hostlimits.SchemaVersion, EffectiveLogicalCPUs: 20} + plan, err := Build(limits, Request{ReserveSystemCores: 4, MinimumWorkers: 8, IncludeFullHostComparison: true}) + if err != nil { + t.Fatal(err) + } + var got []int + for _, candidate := range plan.Candidates { + got = append(got, candidate.Workers) + } + want := []int{8, 12, 16, 20} + if !reflect.DeepEqual(got, want) { + t.Fatalf("candidates = %v, want %v", got, want) + } + if plan.ProductionMaxWorkers != 16 { + t.Fatalf("production max = %d", plan.ProductionMaxWorkers) + } + if plan.Candidates[len(plan.Candidates)-1].Mode != "full_host_comparison" { + t.Fatalf("20-core candidate must be comparison: %+v", plan.Candidates) + } +} + +func TestBudgetCannotExceedVisibleCPUs(t *testing.T) { + limits := hostlimits.Limits{SchemaVersion: hostlimits.SchemaVersion, EffectiveLogicalCPUs: 12} + if _, err := Build(limits, Request{CoreBudget: 16}); err == nil { + t.Fatal("expected core budget error") + } +} From f6751a4446289702001d998a484f819869a214e6 Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:12:19 +0200 Subject: [PATCH 10/23] Expose deployment admission and benchmark planning APIs --- internal/httpapi/deployment_routes.go | 156 ++++++++++++++++++++++++++ 1 file changed, 156 insertions(+) create mode 100644 internal/httpapi/deployment_routes.go diff --git a/internal/httpapi/deployment_routes.go b/internal/httpapi/deployment_routes.go new file mode 100644 index 0000000..f3c24de --- /dev/null +++ b/internal/httpapi/deployment_routes.go @@ -0,0 +1,156 @@ +package httpapi + +import ( + "encoding/json" + "net/http" + "strings" + + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/admission" + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/benchmarkplan" + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/deploymentprofile" + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/hostlimits" + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/hostprofile" +) + +var builtinDeploymentProfiles = deploymentprofile.MustBuiltin() + +func (s *Server) withDeploymentRoutes(next http.Handler) http.Handler { + return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { + switch r.URL.Path { + case "/v1/deployment-profiles": + s.handleDeploymentProfiles(w, r) + return + case "/v1/admission": + s.handleAdmission(w, r) + return + case "/v1/benchmark-plan": + s.handleBenchmarkPlan(w, r) + return + default: + next.ServeHTTP(w, r) + } + }) +} + +func (s *Server) handleDeploymentProfiles(w http.ResponseWriter, r *http.Request) { + if r.Method != http.MethodGet { + s.writeMethodNotAllowed(w, r, http.MethodGet) + return + } + if !s.authorized(r) { + s.writeUnauthorized(w) + return + } + profiles := builtinDeploymentProfiles.List() + s.writeJSON(w, http.StatusOK, map[string]any{ + "api_version": "v1alpha1", + "schema_version": deploymentprofile.SchemaVersion, + "count": len(profiles), + "profiles": profiles, + }) +} + +func (s *Server) handleAdmission(w http.ResponseWriter, r *http.Request) { + if r.Method != http.MethodPost { + s.writeMethodNotAllowed(w, r, http.MethodPost) + return + } + if !s.authorized(r) { + s.writeUnauthorized(w) + return + } + if r.ContentLength > s.config.RequestBodyLimit { + s.writeError(w, http.StatusRequestEntityTooLarge, "request_too_large", "The request body exceeds the configured limit.") + return + } + r.Body = http.MaxBytesReader(w, r.Body, s.config.RequestBodyLimit) + decoder := json.NewDecoder(r.Body) + decoder.DisallowUnknownFields() + var request struct { + Profile string `json:"profile"` + Model string `json:"model"` + Evidence admission.OperatorEvidence `json:"operator_evidence,omitempty"` + } + if err := decoder.Decode(&request); err != nil { + s.writeError(w, http.StatusBadRequest, "invalid_admission_request", "The admission request must be valid JSON using the v1alpha1 contract.") + return + } + profile, ok := builtinDeploymentProfiles.Lookup(strings.TrimSpace(request.Profile)) + if !ok { + s.writeError(w, http.StatusNotFound, "deployment_profile_not_found", "The requested deployment profile does not exist.") + return + } + model, ok := builtinModelRegistry.Lookup(strings.TrimSpace(request.Model)) + if !ok { + s.writeError(w, http.StatusNotFound, "model_not_found", "The requested model is not present in the Quantum Runtime registry.") + return + } + host := hostprofile.Discover() + limits := hostlimits.Discover() + result, err := admission.Evaluate(profile, host, limits, model, request.Evidence) + if err != nil { + s.writeError(w, http.StatusBadRequest, "admission_failed", err.Error()) + return + } + s.writeJSON(w, http.StatusOK, map[string]any{ + "api_version": "v1alpha1", + "admission_schema": admission.SchemaVersion, + "host_schema": hostprofile.SchemaVersion, + "limits_schema": hostlimits.SchemaVersion, + "host": host, + "limits": limits, + "result": result, + }) +} + +func (s *Server) handleBenchmarkPlan(w http.ResponseWriter, r *http.Request) { + if r.Method != http.MethodPost { + s.writeMethodNotAllowed(w, r, http.MethodPost) + return + } + if !s.authorized(r) { + s.writeUnauthorized(w) + return + } + if r.ContentLength > s.config.RequestBodyLimit { + s.writeError(w, http.StatusRequestEntityTooLarge, "request_too_large", "The request body exceeds the configured limit.") + return + } + r.Body = http.MaxBytesReader(w, r.Body, s.config.RequestBodyLimit) + decoder := json.NewDecoder(r.Body) + decoder.DisallowUnknownFields() + var request struct { + Model string `json:"model"` + CoreBudget int `json:"core_budget,omitempty"` + ReserveSystemCores int `json:"reserve_system_cores,omitempty"` + MinimumWorkers int `json:"minimum_workers,omitempty"` + IncludeFullHostComparison bool `json:"include_full_host_comparison,omitempty"` + } + if err := decoder.Decode(&request); err != nil { + s.writeError(w, http.StatusBadRequest, "invalid_benchmark_plan_request", "The benchmark-plan request must be valid JSON using the v1alpha1 contract.") + return + } + model, ok := builtinModelRegistry.Lookup(strings.TrimSpace(request.Model)) + if !ok { + s.writeError(w, http.StatusNotFound, "model_not_found", "The requested model is not present in the Quantum Runtime registry.") + return + } + limits := hostlimits.Discover() + plan, err := benchmarkplan.Build(limits, benchmarkplan.Request{ + CoreBudget: request.CoreBudget, + ReserveSystemCores: request.ReserveSystemCores, + MinimumWorkers: request.MinimumWorkers, + IncludeFullHostComparison: request.IncludeFullHostComparison, + }) + if err != nil { + s.writeError(w, http.StatusBadRequest, "invalid_benchmark_plan_request", err.Error()) + return + } + s.writeJSON(w, http.StatusOK, map[string]any{ + "api_version": "v1alpha1", + "benchmark_schema": benchmarkplan.SchemaVersion, + "canonical_model_id": model.ID, + "limits": limits, + "plan": plan, + }) +} From f25b752236e77f375b40ad306c97192d4dc3039c Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:12:39 +0200 Subject: [PATCH 11/23] Chain deployment and resource routes --- internal/httpapi/registry_routes.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/internal/httpapi/registry_routes.go b/internal/httpapi/registry_routes.go index a543793..a78b3b7 100644 --- a/internal/httpapi/registry_routes.go +++ b/internal/httpapi/registry_routes.go @@ -23,7 +23,7 @@ func (s *Server) withRegistryRoutes(next http.Handler) http.Handler { next.ServeHTTP(w, r) } }) - return s.withResourceRoutes(registry) + return s.withDeploymentRoutes(s.withResourceRoutes(registry)) } func (s *Server) handleModelList(w http.ResponseWriter, r *http.Request) { From 1e75443a4058e1110f38123e7751e08262372153 Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:12:59 +0200 Subject: [PATCH 12/23] Expose guest-aware CPU limits with host resources --- internal/httpapi/resource_routes.go | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/internal/httpapi/resource_routes.go b/internal/httpapi/resource_routes.go index bf054b5..0004856 100644 --- a/internal/httpapi/resource_routes.go +++ b/internal/httpapi/resource_routes.go @@ -7,6 +7,7 @@ import ( "time" "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/calibration" + "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/hostlimits" "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/hostprofile" "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/placement" "github.com/Starlight-Unit-Studio/Quantum-Runtime/internal/resourcecontrol" @@ -49,12 +50,20 @@ func (s *Server) handleHostProfile(w http.ResponseWriter, r *http.Request) { s.writeError(w, http.StatusInternalServerError, "invalid_host_profile", "The discovered host profile is invalid.") return } + limits := hostlimits.Discover() + if err := limits.Validate(); err != nil { + s.logger.Error("invalid host limits", "error", err) + s.writeError(w, http.StatusInternalServerError, "invalid_host_limits", "The discovered process/guest CPU limits are invalid.") + return + } last, calibrated := runtimeResources.LastCalibration() s.writeJSON(w, http.StatusOK, map[string]any{ "api_version": "v1alpha1", "host_schema": hostprofile.SchemaVersion, + "limits_schema": hostlimits.SchemaVersion, "calibration_schema": calibration.SchemaVersion, "host": profile, + "limits": limits, "calibrated": calibrated, "last_calibration": calibrationOrNil(last, calibrated), }) @@ -77,9 +86,11 @@ func (s *Server) handleHostCalibration(w http.ResponseWriter, r *http.Request) { s.writeError(w, http.StatusInternalServerError, "invalid_host_profile", "The discovered host profile is invalid.") return } + limits := hostlimits.Discover() s.writeJSON(w, http.StatusOK, map[string]any{ "api_version": "v1alpha1", "host": host, + "limits": limits, "calibration": result, }) } @@ -115,10 +126,12 @@ func (s *Server) handlePlacement(w http.ResponseWriter, r *http.Request) { s.writeError(w, http.StatusInternalServerError, "invalid_host_profile", "The discovered host profile is invalid.") return } + limits := hostlimits.Discover() s.writeJSON(w, http.StatusOK, map[string]any{ "api_version": "v1alpha1", "placement_schema": placement.SchemaVersion, "host": host, + "limits": limits, "calibration": last, "plan": plan, }) From 9771c4f93961577f5565a2f1049dbee28ce81a12 Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:13:09 +0200 Subject: [PATCH 13/23] Test deployment and benchmark APIs --- internal/httpapi/deployment_routes_test.go | 48 ++++++++++++++++++++++ 1 file changed, 48 insertions(+) create mode 100644 internal/httpapi/deployment_routes_test.go diff --git a/internal/httpapi/deployment_routes_test.go b/internal/httpapi/deployment_routes_test.go new file mode 100644 index 0000000..73c28d2 --- /dev/null +++ b/internal/httpapi/deployment_routes_test.go @@ -0,0 +1,48 @@ +package httpapi + +import ( + "net/http" + "net/http/httptest" + "strings" + "testing" +) + +func TestDeploymentProfilesEndpoint(t *testing.T) { + server := New(testConfig(t), &fakeUpstream{}, testBuild(), discardLogger()) + request := httptest.NewRequest(http.MethodGet, "/v1/deployment-profiles", nil) + response := httptest.NewRecorder() + server.Handler().ServeHTTP(response, request) + if response.Code != http.StatusOK { + t.Fatalf("status = %d body=%s", response.Code, response.Body.String()) + } + if !strings.Contains(response.Body.String(), "ember-production") { + t.Fatalf("E.M.B.E.R. profile missing: %s", response.Body.String()) + } +} + +func TestAdmissionUnknownModelFailsClosed(t *testing.T) { + server := New(testConfig(t), &fakeUpstream{}, testBuild(), discardLogger()) + body := `{"profile":"ember-production","model":"does-not-exist"}` + request := httptest.NewRequest(http.MethodPost, "/v1/admission", strings.NewReader(body)) + request.Header.Set("Content-Type", "application/json") + response := httptest.NewRecorder() + server.Handler().ServeHTTP(response, request) + if response.Code != http.StatusNotFound { + t.Fatalf("status = %d body=%s", response.Code, response.Body.String()) + } +} + +func TestBenchmarkPlanPreservesCanonicalModelIdentity(t *testing.T) { + server := New(testConfig(t), &fakeUpstream{}, testBuild(), discardLogger()) + body := `{"model":"gemma4:26b-a4b-reference","minimum_workers":1}` + request := httptest.NewRequest(http.MethodPost, "/v1/benchmark-plan", strings.NewReader(body)) + request.Header.Set("Content-Type", "application/json") + response := httptest.NewRecorder() + server.Handler().ServeHTTP(response, request) + if response.Code != http.StatusOK { + t.Fatalf("status = %d body=%s", response.Code, response.Body.String()) + } + if !strings.Contains(response.Body.String(), `"canonical_model_id":"gemma4-26b-a4b-reference"`) { + t.Fatalf("canonical identity missing: %s", response.Body.String()) + } +} From f432dcab128d2372d66e296579b2d017ebf95511 Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:13:48 +0200 Subject: [PATCH 14/23] Document observed E.M.B.E.R. deployment generations --- docs/EMBER-DEPLOYMENT-HISTORY.md | 79 ++++++++++++++++++++++++++++++++ 1 file changed, 79 insertions(+) create mode 100644 docs/EMBER-DEPLOYMENT-HISTORY.md diff --git a/docs/EMBER-DEPLOYMENT-HISTORY.md b/docs/EMBER-DEPLOYMENT-HISTORY.md new file mode 100644 index 0000000..5d1df56 --- /dev/null +++ b/docs/EMBER-DEPLOYMENT-HISTORY.md @@ -0,0 +1,79 @@ +# E.M.B.E.R. deployment history and reference classes + +Status: operator-observed deployment evidence used to guide Runtime profiles and benchmark planning. These observations are not generic Quantum Runtime minimum requirements. + +## Why this history matters + +E.M.B.E.R. has run across several hosting generations. The history demonstrates that two different questions must remain separate: + +1. **Can the application construct run?** Small models plus RAG-Lite, long-term memory and the surrounding application stack can run on substantially smaller systems. +2. **Does the host satisfy the current supported E.M.B.E.R. production/intelligence profile?** The current production profile is deliberately stricter and requires a MoE model plus its application-level hardware baseline. + +Quantum Runtime must never turn the production E.M.B.E.R. profile into a global Runtime minimum. + +## Earliest Netcup root-server generation + +The studio reports that the E.M.B.E.R. construct already operated on the smallest Netcup root-server tier in use at the time (about EUR 12/month) when paired with sufficiently small models. RAG-Lite and long-term memory were functional. + +The exact CPU/RAM specification for that historical machine has not yet been recorded in the Runtime evidence set. Runtime therefore does **not** invent or infer concrete minimum values from this observation. + +Classification: **functional compatibility evidence only**. + +## Netcup RS 4000 G12 + +Observed configuration: + +```text +Host CPU class: AMD EPYC 9645 (Turin) +Allocated CPU: 12 dedicated cores +Memory: 32 GB DDR5 ECC +Storage: 1 TB NVMe +Model: Gemma 3 12B Q4 +``` + +This generation is reported as the point at which the E.M.B.E.R. construct became practically usable with Gemma 3 12B Q4 rather than merely operational with smaller models. + +Classification: **historical practical-use reference**, not the current production profile. + +## Netcup RS 12000 G12 - current primary reference + +Operator-provided configuration: + +```text +Host CPU class: AMD EPYC 9645 (Turin), 96-core physical host processor +Guest allocation: 20 dedicated CPU cores +Ember core budget: 16 cores +Memory: 96 GB DDR5 ECC +Storage: approximately 3 TB NVMe SSD, RAID-10 +Network: 2.5 Gbit/s +Virtualization: KVM +Operating system: Debian 13 Trixie +Datacenter: Nuremberg, Germany +``` + +The remaining CPU capacity outside the 16-core Ember budget is intentionally available to the studio website, game and system workload. + +The important Runtime rule is that the CPU model name must **not** turn into a 96-core guest allocation. On KVM, placement and benchmark planning use process affinity, cgroup/cpuset limits and guest-visible topology. Provider guarantees such as "dedicated cores", ECC and memory generation may be supplied as operator evidence when ordinary guest userspace cannot prove them reliably. + +Classification: **current primary production/reference host**. + +## Benchmark implications + +For the current 20-core guest allocation with four cores reserved for other services, the preferred first real-model CPU comparison matrix is: + +```text +8 workers production candidate +12 workers production candidate +16 workers primary Ember production budget +20 workers full-guest comparison only +``` + +Prefill and decode must be recorded separately. A larger worker count is not assumed to be faster, especially on memory-bandwidth-sensitive and MoE workloads. + +## Evidence policy + +- Historical screenshots/operator records may establish an observed configuration or behavior. +- Missing values remain unknown; they are not reconstructed from product names or current provider offerings. +- Provider/virtualization properties that the guest cannot prove are explicit operator evidence, not silently discovered facts. +- Historical ability to run a smaller dense model does not satisfy the current `ember-production` MoE requirement. +- Performance observations become latest-known-good tuning data only after the backend/model/quantization/context/host tuple is recorded reproducibly. From dfb18a537c81f589dff3c671065f71c4f2f0acb0 Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:14:05 +0200 Subject: [PATCH 15/23] Bump Runtime to 0.3.0-alpha.4 --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index 72e5e28..e032775 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -0.3.0-alpha.3 +0.3.0-alpha.4 From b39742284c122dee647eaf8b5b1ed383e9a83a09 Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:14:17 +0200 Subject: [PATCH 16/23] Update build version for alpha.4 --- internal/buildinfo/buildinfo.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/internal/buildinfo/buildinfo.go b/internal/buildinfo/buildinfo.go index 4483c6c..f2d329d 100644 --- a/internal/buildinfo/buildinfo.go +++ b/internal/buildinfo/buildinfo.go @@ -2,7 +2,7 @@ package buildinfo // Values may be replaced with -ldflags during release builds. var ( - Version = "0.3.0-alpha.3" + Version = "0.3.0-alpha.4" Commit = "development" BuildDate = "unknown" ) From 36db2dfbe0a3a2d41f29561887f0097e1f1dc1c5 Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:14:54 +0200 Subject: [PATCH 17/23] Document Runtime 0.3.0-alpha.4 --- CHANGELOG.md | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index d6ea829..2a49243 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,18 @@ # Changelog +## 0.3.0-alpha.4 - 2026-09-06 + +- Added `quantum.runtime/deployment-profile/v1alpha1` with a builtin `ember-production` application profile kept separate from generic Quantum Runtime minimums. +- Encoded the current supported E.M.B.E.R. production requirements as 64 GiB memory, ECC required, DDR5 preferred, 8 physical cores, GPU optional and MoE architecture mandatory; the historical ~2.6 GHz reference remains advisory only. +- Added `quantum.runtime/admission-result/v1alpha1` with explicit `admitted`, `rejected` and `needs_operator_evidence` decisions and per-requirement evidence instead of guessing missing ECC/provider facts. +- Added guest/process CPU-limit discovery from process affinity, cgroup cpusets and CPU quota plus virtualization evidence so an EPYC host model name cannot imply that all host-physical cores are allocated to a KVM guest. +- Added operator core-budget evidence so application admission can reserve guest CPU capacity for other services without changing global Runtime topology. +- Added `quantum.runtime/model-benchmark-plan/v1alpha1` to generate repeatable CPU worker-count matrices without claiming unmeasured throughput; a 20-core guest with four reserved system cores produces the intended 8/12/16 production candidates plus an optional 20-core full-host comparison. +- Added `/v1/deployment-profiles`, `/v1/admission` and `/v1/benchmark-plan`; `/v1/host`, calibration and placement responses now also expose guest/process CPU limits. +- Added `docs/EMBER-DEPLOYMENT-HISTORY.md` distinguishing historical functional compatibility with small models/RAG-Lite/LTM from the current supported E.M.B.E.R. production/intelligence profile. +- Recorded the RS 4000 G12 (12 dedicated cores, 32 GB DDR5 ECC, 1 TB NVMe, Gemma 3 12B Q4) as a historical practical-use reference and the RS 12000 G12 (20 dedicated guest cores, 96 GB DDR5 ECC, ~3 TB NVMe RAID-10, KVM, Debian 13, 16-core Ember budget) as the current primary reference host. +- Kept exact hardware for the earliest low-cost Netcup root-server generation unknown rather than reconstructing missing values from current product offerings. + ## 0.3.0-alpha.3 - 2026-09-05 - Added `quantum.runtime/host-profile/v1alpha1` Linux discovery for CPU vendor/model/features, physical/logical CPUs, SMT ratio, NUMA nodes, RAM/huge-page metadata, block/NVMe devices and visible AMD/NVIDIA/Intel accelerator metadata. @@ -140,4 +153,4 @@ Initial Quantum Runtime foundation. - Quantum native chat API - OpenAI-compatible API - GPU scheduling -- Quantum CoreOS TCI runtime integration \ No newline at end of file +- Quantum CoreOS TCI runtime integration From 795e1398e59b1bb612c553e8b1b851dd7e36b637 Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:15:26 +0200 Subject: [PATCH 18/23] Update README for alpha.4 admission layer --- README.md | 61 ++++++++++++++++++++++++++++++++++++++++++++++++------- 1 file changed, 54 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index 5ea1d82..40e9f14 100644 --- a/README.md +++ b/README.md @@ -4,7 +4,7 @@ Quantum Runtime is the independent AI runtime and model-service project of Starlight Unit Studios. -Current version: `0.3.0-alpha.3` +Current version: `0.3.0-alpha.4` ## Current alpha scope @@ -14,6 +14,7 @@ Quantum Runtime 0.3 adds the first model- and engine-neutral backend capability 2. the versioned model identity and read-only registry contract 3. a non-destructive Linux service package that can be installed beside an existing Ollama service 4. host-resource discovery, bounded calibration and a CPU-first placement contract for RAM/VRAM/NVMe candidates +5. application deployment-profile admission, guest/process CPU-limit discovery and repeatable real-model benchmark planning Quantum Runtime now has two local execution paths. Ollama remains the default adoption/fallback mode, while a direct llama.cpp path can talk to `llama-server` without an Ollama daemon in the inference request path: @@ -43,9 +44,13 @@ The initial llama.cpp adapter deliberately uses the external `llama-server` proc - Ollama chat/generate/embed compatibility translation to llama.cpp OpenAI-style endpoints - fail-closed handling for llama.cpp features not yet normalized: vision, tools, reasoning control and structured output - Linux host discovery for CPU topology/features, NUMA, RAM/huge pages, block/NVMe devices and visible accelerator/VRAM metadata +- guest/process CPU-limit discovery from affinity, cgroup cpusets and CPU quota with virtualization evidence - explicit bounded memory-bandwidth/worker-count calibration rather than automatic startup benchmarking - versioned CPU-first placement plans that prefer RAM/CPU when the hot set fits and only consider hybrid acceleration after CPU capacity fails - explicit NVMe cold-tier placement; hot execution state is never silently spilled to disk +- machine-readable application deployment profiles separate from generic Runtime minimums +- E.M.B.E.R. production admission with explicit `admitted`, `rejected` and `needs_operator_evidence` decisions +- repeatable real-model CPU benchmark-plan generation without claiming unmeasured throughput - streamed forwarding/translation, cancellation, body limits and backend timeouts - loopback-only default on `127.0.0.1:11450` - bearer-token requirement for any non-loopback bind @@ -78,6 +83,7 @@ curl -s http://127.0.0.1:11450/v1/backends curl -s http://127.0.0.1:11450/v1/model-policies curl -s http://127.0.0.1:11450/v1/upstreams curl -s http://127.0.0.1:11450/v1/host +curl -s http://127.0.0.1:11450/v1/deployment-profiles curl -s -X POST http://127.0.0.1:11450/v1/host/calibrate ``` @@ -116,9 +122,9 @@ The machine-readable schema lives at: schema/model-manifest-v1alpha1.schema.json ``` -Builtin contract/profile examples live under `internal/modelregistry/data/` for a generic model, Ember CoreUI and the future Quantum CoreOS Gemma 4 e4b TCI profile. +Builtin contract/profile examples live under `internal/modelregistry/data/` for a generic model, Ember CoreUI, Gemma 4 26B A4B MoE reference and the future Quantum CoreOS Gemma 4 e4b TCI profile. -The manifest separates canonical model identity from aliases, source revision, backend, artifacts, SHA-256 integrity, capabilities, compatibility, persona package, lifecycle state and provenance. In 0.3, artifacts may additionally declare their own backend/format/role, allowing one canonical identity to acquire multiple backend artifacts without changing the client-facing model ID. Generic architecture metadata now distinguishes dense, MoE and unknown profiles and can carry context-policy and expert-topology data without exposing family-specific fields in the public API. An `unverified` example is a contract/profile reference, not a cryptographic claim about unresolved model artifacts. +The manifest separates canonical model identity from aliases, source revision, backend, artifacts, SHA-256 integrity, capabilities, compatibility, persona package, lifecycle state and provenance. In 0.3, artifacts may additionally declare their own backend/format/role, allowing one canonical identity to acquire multiple backend artifacts without changing the client-facing model ID. Generic architecture metadata distinguishes dense, MoE and unknown profiles and can carry context-policy and expert-topology data without exposing family-specific fields in the public API. An `unverified` example is a contract/profile reference, not a cryptographic claim about unresolved model artifacts. ## Direct llama.cpp backend @@ -141,11 +147,51 @@ If the llama.cpp server uses `--api-key`, set `QUANTUM_RUNTIME_LLAMA_CPP_API_KEY ## CPU-first host placement -`0.3.0-alpha.3` adds the first generic hardware/resource contract. `GET /v1/host` reports OS-visible CPU, NUMA, RAM, storage and accelerator metadata. `POST /v1/host/calibrate` runs an explicit bounded synthetic memory/worker sweep. `POST /v1/placement` creates a pre-activation capacity plan for model weights, MoE experts, caches, projectors, workspace and an optional explicit cold NVMe tier. +`0.3.0-alpha.3` added the first generic hardware/resource contract. `GET /v1/host` reports OS-visible CPU, NUMA, RAM, storage and accelerator metadata. `POST /v1/host/calibrate` runs an explicit bounded synthetic memory/worker sweep. `POST /v1/placement` creates a pre-activation capacity plan for model weights, MoE experts, caches, projectors, workspace and an optional explicit cold NVMe tier. + +`0.3.0-alpha.4` adds a separate guest/process limit view. CPU affinity and cgroup cpusets define the usable guest/process CPU set; cgroup CPU quota is reported independently. Virtualization evidence is surfaced so a physical host model such as a 96-core EPYC 9645 cannot silently become a 96-core Runtime allocation when a KVM guest was allocated fewer cores. CPU/RAM remains the baseline. A visible GPU does not automatically win: if the hot working set fits usable RAM, the first planner returns `cpu_only`. Hybrid placement is only considered after CPU-only capacity fails and acceleration was explicitly allowed. NVMe is never used as an implicit escape hatch for hot state. -This is a truthful capacity/host foundation, not yet a claim of measured model throughput. Real backend/model prefill/decode calibration, NUMA affinity, thread pinning, GGUF size estimation and backend activation from placement plans remain later Runtime 0.3 slices. See `docs/HARDWARE-PLACEMENT.md`. +## E.M.B.E.R. production admission + +`ember-production` is an **application profile**, not a generic Runtime minimum. The current profile requires 64 GiB memory, ECC, at least eight physical cores and an MoE model. DDR5 is preferred. A GPU is optional. The historical ~2.6 GHz/core figure remains advisory and is never a hard admission cutoff. + +Properties that ordinary guest userspace cannot prove reliably remain `unknown`. Operator evidence can be supplied explicitly, for example on the current KVM deployment: + +```bash +curl -s -X POST http://127.0.0.1:11450/v1/admission \ + -H 'Content-Type: application/json' \ + -d '{ + "profile":"ember-production", + "model":"gemma4:26b-a4b-reference", + "operator_evidence":{ + "ecc_verified":true, + "memory_class":"ddr5", + "dedicated_physical_cores":20, + "core_budget":16 + } + }' +``` + +A dense model fails the MoE production requirement instead of being silently substituted while preserving the E.M.B.E.R. profile identity. + +## Real-model CPU benchmark planning + +`POST /v1/benchmark-plan` creates the worker-count matrix for a canonical model without running or inventing benchmark results. Example for a 20-core guest where four cores remain reserved for website/game/system workload: + +```bash +curl -s -X POST http://127.0.0.1:11450/v1/benchmark-plan \ + -H 'Content-Type: application/json' \ + -d '{ + "model":"gemma4:26b-a4b-reference", + "reserve_system_cores":4, + "minimum_workers":8, + "include_full_host_comparison":true + }' +``` + +On a 20-core effective guest allocation this yields 8/12/16 production candidates and a 20-core full-host comparison. Prefill and decode measurements still have to be collected separately for the exact backend/model/quantization/context tuple before Runtime can prefer one candidate. ## Ember CoreUI adoption @@ -202,7 +248,7 @@ The process rejects a network-wide bind when no bearer token is configured. ```text Quantum Runtime model identity, lifecycle, inference APIs, streaming, backend adapters, - host discovery, calibration and placement policy + host discovery, calibration, placement and application-profile admission Quantum Control server, hosting, service, database, backup and update management @@ -218,6 +264,7 @@ Quantum CoreOS consumes released Quantum Runtime packages rather than maintainin - `docs/ARCHITECTURE.md` - `docs/API.md` - `docs/HARDWARE-PLACEMENT.md` +- `docs/EMBER-DEPLOYMENT-HISTORY.md` - `docs/INSTALLATION.md` - `docs/ROADMAP.md` - `docs/SECURITY.md` @@ -230,4 +277,4 @@ Quantum Runtime project-owned code is licensed under the **Starlight Unit Studio Private/internal use, internal commercial use and Integrated Application Use are permitted under the license conditions. Quantum Runtime itself may not be sold, white-labeled or offered as a paid standalone general-purpose Runtime service. Third-party inference engines, models, model weights, datasets and tools retain their own terms. -The legally controlling German text is `LICENSE.de.md`; `LICENSE.md` is an English convenience translation. This is a custom Source Available license and is not an OSI-approved open-source license. \ No newline at end of file +The legally controlling German text is `LICENSE.de.md`; `LICENSE.md` is an English convenience translation. This is a custom Source Available license and is not an OSI-approved open-source license. From aa6fa54a24ae9d022d1cb29ad4ed0b32b44b4416 Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:17:03 +0200 Subject: [PATCH 19/23] gofmt benchmark plan --- internal/benchmarkplan/plan.go | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/internal/benchmarkplan/plan.go b/internal/benchmarkplan/plan.go index ce46dfa..d6d62a0 100644 --- a/internal/benchmarkplan/plan.go +++ b/internal/benchmarkplan/plan.go @@ -22,12 +22,12 @@ type Candidate struct { } type Plan struct { - SchemaVersion string `json:"schema_version"` - EffectiveHostCPUs int `json:"effective_host_cpus"` - ProductionMaxWorkers int `json:"production_max_workers"` - ReservedSystemCores int `json:"reserved_system_cores"` - Candidates []Candidate `json:"candidates"` - Notes []string `json:"notes,omitempty"` + SchemaVersion string `json:"schema_version"` + EffectiveHostCPUs int `json:"effective_host_cpus"` + ProductionMaxWorkers int `json:"production_max_workers"` + ReservedSystemCores int `json:"reserved_system_cores"` + Candidates []Candidate `json:"candidates"` + Notes []string `json:"notes,omitempty"` } func Build(limits hostlimits.Limits, req Request) (Plan, error) { From fa4c842c06f802592a9184e16e4ae5c32a44b73c Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:17:26 +0200 Subject: [PATCH 20/23] gofmt admission tests --- internal/admission/admission_test.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/internal/admission/admission_test.go b/internal/admission/admission_test.go index 79a5a59..4ce9ae5 100644 --- a/internal/admission/admission_test.go +++ b/internal/admission/admission_test.go @@ -90,8 +90,8 @@ func emberProfile(t *testing.T) deploymentprofile.Profile { func suitableHost() hostprofile.Profile { return hostprofile.Profile{ SchemaVersion: hostprofile.SchemaVersion, - CPU: hostprofile.CPUProfile{PhysicalCores: 20, LogicalCores: 20, ThreadsPerCore: 1}, - Memory: hostprofile.MemoryProfile{TotalBytes: 96 << 30, AvailableBytes: 80 << 30}, + CPU: hostprofile.CPUProfile{PhysicalCores: 20, LogicalCores: 20, ThreadsPerCore: 1}, + Memory: hostprofile.MemoryProfile{TotalBytes: 96 << 30, AvailableBytes: 80 << 30}, } } From 87fea513a92ef00b7afe05dc111e2928142b475c Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:18:05 +0200 Subject: [PATCH 21/23] gofmt host limit discovery --- internal/hostlimits/limits.go | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/internal/hostlimits/limits.go b/internal/hostlimits/limits.go index 2727dc3..e102a3e 100644 --- a/internal/hostlimits/limits.go +++ b/internal/hostlimits/limits.go @@ -14,16 +14,16 @@ import ( const SchemaVersion = "quantum.runtime/host-limits/v1alpha1" type Limits struct { - SchemaVersion string `json:"schema_version"` - CollectedAt time.Time `json:"collected_at"` - EffectiveLogicalCPUs int `json:"effective_logical_cpus"` - AffinityCPUList string `json:"affinity_cpu_list,omitempty"` - AffinityLogicalCPUs int `json:"affinity_logical_cpus,omitempty"` - CgroupCPUSet string `json:"cgroup_cpuset,omitempty"` - CgroupCPUSetLogicalCPUs int `json:"cgroup_cpuset_logical_cpus,omitempty"` - CPUQuotaCores float64 `json:"cpu_quota_cores,omitempty"` - Virtualization Virtualization `json:"virtualization"` - Warnings []string `json:"warnings,omitempty"` + SchemaVersion string `json:"schema_version"` + CollectedAt time.Time `json:"collected_at"` + EffectiveLogicalCPUs int `json:"effective_logical_cpus"` + AffinityCPUList string `json:"affinity_cpu_list,omitempty"` + AffinityLogicalCPUs int `json:"affinity_logical_cpus,omitempty"` + CgroupCPUSet string `json:"cgroup_cpuset,omitempty"` + CgroupCPUSetLogicalCPUs int `json:"cgroup_cpuset_logical_cpus,omitempty"` + CPUQuotaCores float64 `json:"cpu_quota_cores,omitempty"` + Virtualization Virtualization `json:"virtualization"` + Warnings []string `json:"warnings,omitempty"` } type Virtualization struct { From 0284afcd8245f1cbd18e682d0e2b5b1dc77d3ac1 Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:20:25 +0200 Subject: [PATCH 22/23] Normalize virtualization evidence before classification --- internal/hostlimits/limits.go | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/internal/hostlimits/limits.go b/internal/hostlimits/limits.go index e102a3e..49f8291 100644 --- a/internal/hostlimits/limits.go +++ b/internal/hostlimits/limits.go @@ -186,9 +186,9 @@ func discoverVirtualization() Virtualization { if err != nil { continue } - value := strings.ToLower(strings.TrimSpace(string(data))) + value := strings.TrimSpace(string(data)) if kind := virtualizationKind(value); kind != "" { - return Virtualization{Guest: true, Kind: kind, Evidence: item.label + ": " + strings.TrimSpace(string(data))} + return Virtualization{Guest: true, Kind: kind, Evidence: item.label + ": " + value} } } @@ -199,6 +199,7 @@ func discoverVirtualization() Virtualization { } func virtualizationKind(value string) string { + value = strings.ToLower(strings.TrimSpace(value)) switch { case strings.Contains(value, "kvm"), strings.Contains(value, "qemu"): return "kvm" From 1387441003ecd9305469235c8b15656ac6a99059 Mon Sep 17 00:00:00 2001 From: Starlight Unit Studios Date: Sun, 6 Sep 2026 01:22:31 +0200 Subject: [PATCH 23/23] Document alpha.4 admission and benchmark APIs --- docs/API.md | 113 +++++++++++++++++++++++++++++++++++++++++++++++----- 1 file changed, 102 insertions(+), 11 deletions(-) diff --git a/docs/API.md b/docs/API.md index 9e18178..abd59c9 100644 --- a/docs/API.md +++ b/docs/API.md @@ -16,13 +16,13 @@ Example response: { "status": "alive", "service": "quantum-runtime", - "version": "0.2.0-alpha.1" + "version": "0.3.0-alpha.4" } ``` ### `GET /readyz` -Checks whether the configured initial backend answers its version probe. Returns HTTP 503 when inference is unavailable. +Checks whether the configured inference backend is ready. Returns HTTP 503 when inference is unavailable. ### `GET /v1/runtime` @@ -42,7 +42,7 @@ Example shape: { "api_version": "v1alpha1", "schema_version": "quantum.runtime/model-manifest/v1alpha1", - "count": 3, + "count": 4, "models": [ { "id": "ember-coreui", @@ -86,7 +86,7 @@ Unknown identifiers fail with HTTP 404: } ``` -The registry is read-only in `0.2.0-alpha.1`. Install, remove, load and unload operations are intentionally not implemented yet. +The registry remains read-only. Install, remove, load and unload operations are intentionally separate from the current registry contract. ## Model manifest contract @@ -149,7 +149,7 @@ The Ollama mutation switch is a compatibility-proxy policy only. It does not imp ## Streaming -Quantum Runtime forwards upstream streaming responses incrementally and flushes chunks to the client. It does not buffer a complete model answer before sending it. +Quantum Runtime forwards or translates upstream streaming responses incrementally and flushes chunks to the client. It does not buffer a complete model answer before sending it. ## Authentication @@ -161,7 +161,7 @@ When `QUANTUM_RUNTIME_AUTH_TOKEN` is configured, protected native and compatibil Authorization: Bearer ``` -The Runtime bearer token, cookies and forwarding headers are stripped before a request reaches the initial Ollama backend. +The Runtime bearer token, cookies and forwarding headers are stripped before a request reaches an inference backend. Optional llama.cpp credentials use their own configuration and are never copied from Runtime bearer credentials. `/healthz` and `/readyz` remain available for local service supervision. @@ -179,8 +179,6 @@ Runtime-generated errors use: } ``` -Upstream Ollama responses are preserved for compatibility after a request has been accepted and forwarded. - ## Compatibility promise `v1alpha1` is intentionally not a stable 1.0 contract. Changes must be documented in `CHANGELOG.md`. @@ -203,8 +201,7 @@ The response contains `requested_identifier`, `canonical_model_id`, selected bac `GET /v1/upstreams` exposes the tested-upstream ledger plus the subset currently eligible as `latest_known_good`. An `observed-unpinned` entry is informative only and cannot be promoted automatically. - -## llama.cpp direct compatibility bridge (0.3.0-alpha.2) +## llama.cpp direct compatibility bridge (0.3.0-alpha.2+) When `QUANTUM_RUNTIME_BACKEND=llama.cpp`, the existing application-facing Ollama compatibility routes are translated to a directly configured `llama-server`; Ollama is not present in that request path. @@ -213,6 +210,100 @@ When `QUANTUM_RUNTIME_BACKEND=llama.cpp`, the existing application-facing Ollama - `/api/embed` and `/api/embeddings` -> `/v1/embeddings` - `/api/tags`, `/api/show`, `/api/ps` and `/api/version` are synthesized from the configured Runtime model identity because llama.cpp does not expose Ollama's model-store contract -The configured `QUANTUM_RUNTIME_LLAMA_CPP_MODEL` must match the client-visible model identifier. A mismatched model request returns an error instead of silently substituting another canonical identity. Only `temperature`, `top_p` and `top_k` are normalized from the current Ollama `options` object in this first direct slice. Per-request `num_ctx`, predict/thread/repeat/seed/stop tuning is not injected. +The configured `QUANTUM_RUNTIME_LLAMA_CPP_MODEL` must match the client-visible model identifier. A mismatched model request returns an error instead of silently substituting another canonical identity. Only `temperature`, `top_p` and `top_k` are normalized from the current Ollama `options` object in this direct path. Per-request `num_ctx`, predict/thread/repeat/seed/stop tuning is not injected. Vision, tool calls/tool history, explicit reasoning control and structured-output requests currently return `422 unsupported_backend_capability` on this direct adapter. This is intentional: the backend contract must not claim a capability until Runtime preserves its semantics end to end. Streaming content is translated from llama.cpp SSE to Ollama NDJSON; llama.cpp `reasoning_content`/`reasoning` deltas are preserved as the Ollama-compatible `message.thinking` field when present. + +## Host discovery, calibration and placement (0.3.0-alpha.3+) + +`GET /v1/host` returns the current host profile using `quantum.runtime/host-profile/v1alpha1`. The Linux discovery path reports OS-visible CPU topology/features, NUMA nodes, RAM and huge-page metadata, storage/NVMe devices and visible accelerator metadata. + +`POST /v1/host/calibrate` runs an explicit bounded synthetic memory copy/read and worker-count sweep. It is not a model tokens-per-second benchmark. + +`POST /v1/placement` creates a pre-activation CPU-first capacity plan using separate model-weight, MoE-expert, KV-cache, prefix-cache, projector, workspace and explicit cold-tier memory classes. A visible accelerator does not automatically win, and hot inference state is never silently spilled to disk. + +## Guest/process CPU limits (0.3.0-alpha.4) + +`GET /v1/host`, calibration and placement responses now include a separate `limits` object using `quantum.runtime/host-limits/v1alpha1`. + +The hardware profile and effective guest/process limits are deliberately distinct. Runtime evaluates: + +- the process `Cpus_allowed_list` +- cgroup cpuset limits where exposed +- cgroup CPU quota as a separate scheduling signal +- virtualization evidence where available + +A physical CPU model name never implies that all host cores are allocated to a virtual machine. For example, an AMD EPYC 9645 host may physically contain 96 cores while a KVM guest exposes and is allowed to use a much smaller dedicated CPU set. + +## Application deployment profiles + +`GET /v1/deployment-profiles` returns `quantum.runtime/deployment-profile/v1alpha1` profiles. + +The builtin `ember-production` profile is application-specific and does not become a generic Quantum Runtime minimum. Its current policy is: + +```text +memory minimum: 64 GiB +ECC: required +memory class: DDR5 preferred +physical CPU cores: 8 minimum +reference clock: ~2600 MHz advisory only +accelerator: optional +model architecture: MoE required +``` + +The raw clock reference is never used as a hard admission cutoff. Calibrated performance, CPU capabilities and memory/topology evidence are preferred when available. + +## E.M.B.E.R. admission + +`POST /v1/admission` evaluates a deployment profile against a canonical model and the current host/guest evidence. + +Example for a provider-verified KVM deployment: + +```json +{ + "profile": "ember-production", + "model": "gemma4:26b-a4b-reference", + "operator_evidence": { + "ecc_verified": true, + "memory_class": "ddr5", + "dedicated_physical_cores": 20, + "core_budget": 16 + } +} +``` + +The result uses `quantum.runtime/admission-result/v1alpha1` and returns one of: + +- `admitted` +- `rejected` +- `needs_operator_evidence` + +Properties that normal guest userspace cannot prove reliably, such as provider-guaranteed ECC or dedicated physical cores, remain explicit operator evidence rather than guessed facts. Unknown mandatory evidence therefore produces `needs_operator_evidence`. A dense model cannot satisfy a profile requiring `architecture_class=moe` merely because it belongs to an otherwise supported model family. + +`core_budget` is an application scheduling boundary, not a claim about host topology. It lets an operator keep part of a guest allocation free for other services while admitting E.M.B.E.R. against a smaller production budget. + +## Real-model CPU benchmark planning + +`POST /v1/benchmark-plan` creates a repeatable worker-count experiment matrix for a canonical model. It does not start inference and does not invent benchmark values. + +Example: + +```json +{ + "model": "gemma4:26b-a4b-reference", + "reserve_system_cores": 4, + "minimum_workers": 8, + "include_full_host_comparison": true +} +``` + +On a 20-CPU effective guest allocation, this produces: + +```text +8 workers production candidate +12 workers production candidate +16 workers production candidate +20 workers full-host comparison +``` + +The benchmark plan is only an experiment definition. Prefill throughput, decode throughput, TTFT, memory footprint and the exact backend/model/quantization/context tuple still require real measurements before Runtime can promote a worker count or placement to latest-known-good.