import pyopencl as cl
import numpy as np
import time

# -------------------------------
# Constants
# -------------------------------
PHI = 1.6180339887
SQRT_PHI = PHI ** 0.5
INSTANCES = 8
SLOTS_PER_INSTANCE = 64      # Expanded to hold "virtual memory pages"
SUPERVISOR_TICKS = 200
MEMORY_PAGE_SIZE = 16        # Minimal page for tasks

# Minimal "Debian tasks" per instance
DEBIAN_TASKS = [
    ["init", "network", "filesystem", "scheduler"],
    ["init", "ssh", "logger", "scheduler"],
    ["init", "cron", "filesystem", "monitor"],
    ["init", "network", "scheduler", "logger"],
    ["init", "scheduler", "monitor", "cron"],
    ["init", "filesystem", "network", "logger"],
    ["init", "monitor", "scheduler", "ssh"],
    ["init", "network", "cron", "monitor"]
]

# -------------------------------
# OpenCL setup
# -------------------------------
platforms = cl.get_platforms()
device = platforms[0].get_devices()[0]
ctx = cl.Context([device])
queue = cl.CommandQueue(ctx)
mf = cl.mem_flags

# Supervisor + syscall kernel
kernel_source = """
__kernel void lattice_evolve_syscall(
    __global float *lattice,
    __global float *workspace,
    __global int *syscall_requests,
    const float threshold,
    const int slots_per_instance
) {
    int gid = get_global_id(0);
    int instance = gid / slots_per_instance;
    int slot = gid % slots_per_instance;

    // Step 1: Evolve lattice
    float val = workspace[gid];
    lattice[gid] = val >= threshold ? 1.0f : 0.0f;

    if(instance > 0)
        lattice[gid] = 0.5f * (lattice[gid] + lattice[gid - slots_per_instance]);

    workspace[gid] = val + 0.01f * (instance + 1);

    // Step 2: Minimal syscall layer (example: write to "virtual memory")
    if(syscall_requests[instance] == 1 && slot < 4) {
        lattice[gid] = 2.0f; // signal write completion
    }
}
"""
program = cl.Program(ctx, kernel_source).build()
kernel = program.lattice_evolve_syscall

# -------------------------------
# Buffers
# -------------------------------
total_slots = INSTANCES * SLOTS_PER_INSTANCE
lattice_host = np.zeros(total_slots, dtype=np.float32)
workspace_host = np.random.uniform(SQRT_PHI, 2*SQRT_PHI, total_slots).astype(np.float32)
syscall_requests_host = np.zeros(INSTANCES, dtype=np.int32)

lattice_buf = cl.Buffer(ctx, mf.READ_WRITE | mf.COPY_HOST_PTR, hostbuf=lattice_host)
workspace_buf = cl.Buffer(ctx, mf.READ_WRITE | mf.COPY_HOST_PTR, hostbuf=workspace_host)
syscall_buf = cl.Buffer(ctx, mf.READ_WRITE | mf.COPY_HOST_PTR, hostbuf=syscall_requests_host)

kernel.set_args(lattice_buf, workspace_buf, syscall_buf, np.float32(SQRT_PHI), np.int32(SLOTS_PER_INSTANCE))

# -------------------------------
# Supervisor + Debian slot loader loop
# -------------------------------
print("HDGL Supervisor: Launching full Debian virtual environment...\n")

for tick in range(SUPERVISOR_TICKS):
    # Randomly request a syscall from instances (simulate disk/network)
    if tick % 30 == 0:
        syscall_requests_host[np.random.randint(0, INSTANCES)] = 1
        cl.enqueue_copy(queue, syscall_buf, syscall_requests_host)

    cl.enqueue_nd_range_kernel(queue, kernel, (total_slots,), None)

    if tick % 20 == 0:
        cl.enqueue_copy(queue, lattice_host, lattice_buf)

        print(f"[Tick {tick}] Instance lattice + virtual memory:")
        for i in range(INSTANCES):
            slice_start = i * SLOTS_PER_INSTANCE
            slice_end = slice_start + SLOTS_PER_INSTANCE
            line = ''.join(['#' if val >= 1 else '.' for val in lattice_host[slice_start:slice_end]])
            # Display Debian tasks "activated" according to first 4 slots
            tasks_status = ["OK" if lattice_host[slice_start+j] >= 1 else "--" for j in range(4)]
            syscall_status = "SYS" if syscall_requests_host[i] == 1 else "--"
            print(f"  Instance {i+1}: {line}  Tasks: {dict(zip(DEBIAN_TASKS[i], tasks_status))}  Syscall: {syscall_status}")

    # Reset syscall requests after execution
    syscall_requests_host[:] = 0
    cl.enqueue_copy(queue, syscall_buf, syscall_requests_host)
    time.sleep(0.01)

print("\nFull virtual Debian environment booted inside HDGL lattice supervisor.")
