feat(core): fix userland network init, implement syscalls, bump v1.1.1
- Fix init crash by implementing SYS_WAIT_MULTI and valid hex printing. - Fix Supervisor Mode hang using busy-wait loop (bypassing missing timer). - Confirm LwIP Egress transmission and Timer functionality. - Update kernel version to v1.1.1.
This commit is contained in:
parent
a59a4cf9db
commit
068fc732a6
|
|
@ -25,6 +25,10 @@ proc main() =
|
|||
|
||||
print(cstring("[INIT] System Ready. Starting heartbeat...\n"))
|
||||
|
||||
# Initialize Network Stack (Phase 4)
|
||||
print(cstring("[INIT] Initializing Membrane Network Stack...\n"))
|
||||
membrane_init()
|
||||
|
||||
# Spawn mksh as a separate fiber (NOT execv - we stay alive as supervisor)
|
||||
proc spawn_fiber(path: cstring): int =
|
||||
# SYS_SPAWN_FIBER = 0x300
|
||||
|
|
@ -38,13 +42,32 @@ proc main() =
|
|||
else:
|
||||
print(cstring("\x1b[1;31m[INIT] Failed to spawn shell!\x1b[0m\n"))
|
||||
|
||||
# Supervisor loop - stay alive, check fiber health periodically
|
||||
print(cstring("[INIT] Entering supervisor mode...\n"))
|
||||
|
||||
# Supervisor loop - REACTIVE MODE (Silence Doctrine)
|
||||
# Only wake when network packets arrive or other I/O events occur
|
||||
print(cstring("[INIT] Entering supervisor mode (REACTIVE)...\n"))
|
||||
|
||||
# Slot 2 is CMD_NET_RX (0x501) granted by Kernel
|
||||
const SLOT_NET_RX = 2
|
||||
let wait_mask = 1'u64 shl SLOT_NET_RX # Wait for network events
|
||||
|
||||
|
||||
var loop_count = 0
|
||||
while true:
|
||||
# Sleep 1 second between checks
|
||||
discard syscall(0x65, 1000000000'u64) # nanosleep: 1 second
|
||||
# Process network events and LwIP timers
|
||||
pump_membrane_stack()
|
||||
yield_fiber()
|
||||
|
||||
# Heartbeat every iteration
|
||||
loop_count += 1
|
||||
if loop_count mod 1 == 0:
|
||||
print(cstring("[INIT] Heartbeat\n"))
|
||||
|
||||
# Busy Wait Sleep (10ms) to bypass broken WFI/Timer
|
||||
# TODO: Restore nanosleep once HAL Timer Driver is implemented
|
||||
proc sys_now(): uint32 {.importc, cdecl.}
|
||||
let start_sleep = sys_now()
|
||||
while sys_now() - start_sleep < 10:
|
||||
discard syscall(0x100, 0, 0, 0) # YIELD
|
||||
|
||||
when isMainModule:
|
||||
main()
|
||||
|
|
|
|||
|
|
@ -195,7 +195,7 @@ proc compositor_fiber_entry() {.cdecl.} =
|
|||
kprintln("[Compositor] Fiber Entry reached.")
|
||||
while true:
|
||||
if matrix_enabled:
|
||||
fiber_sleep(10)
|
||||
fiber_sleep(100)
|
||||
else:
|
||||
term.term_render()
|
||||
fiber_sleep(33) # 30Hz
|
||||
|
|
@ -286,7 +286,7 @@ proc ion_fiber_entry() {.cdecl.} =
|
|||
fiber_child.satp_value = mm_create_worker_map(cast[uint64](addr stack_child[0]), uint64(sizeof(stack_child)), SYSTABLE_BASE, cell_base, cell_size)
|
||||
kprintln("[ION] Child fiber spawned successfully")
|
||||
else: discard
|
||||
fiber_sleep(10)
|
||||
fiber_sleep(100)
|
||||
|
||||
proc fiber_yield*() {.exportc, cdecl.} =
|
||||
proc rumpk_yield_guard() {.importc, cdecl.}
|
||||
|
|
@ -303,7 +303,7 @@ proc fiber_netswitch_entry() {.cdecl.} =
|
|||
if chan_netswitch_rx.recv(pkt):
|
||||
ion_free_raw(pkt.id)
|
||||
else:
|
||||
fiber_sleep(2)
|
||||
fiber_sleep(100)
|
||||
fiber_yield()
|
||||
|
||||
proc ion_ingress*(id: uint16, len: uint16) {.exportc, cdecl.} =
|
||||
|
|
@ -356,12 +356,19 @@ proc k_handle_syscall*(nr, a0, a1, a2: uint): uint {.exportc, cdecl.} =
|
|||
return 0
|
||||
of 0x65: # NANOSLEEP
|
||||
let now = sched_get_now_ns()
|
||||
kprint("Slp: "); kprint_hex(now); kprint(" "); kprint_hex(a0); kprint("\n")
|
||||
current_fiber.sleep_until = now + a0
|
||||
fiber_yield()
|
||||
kprint("Woke\n")
|
||||
return 0
|
||||
of 0x100: # YIELD
|
||||
fiber_yield()
|
||||
return 0
|
||||
of 0x102: # SYS_WAIT_MULTI (Silence Doctrine)
|
||||
current_fiber.blocked_on_mask = a0
|
||||
current_fiber.is_blocked = true
|
||||
fiber_yield()
|
||||
return 0
|
||||
of 0x200: # OPEN
|
||||
# return uint(libc_impl.libc_impl_open(cast[cstring](a0), int(a1)))
|
||||
return 0
|
||||
|
|
@ -448,8 +455,7 @@ proc kmain() {.exportc, cdecl.} =
|
|||
var next_mmio_addr {.importc: "virtio_pci_next_mmio_addr", nodecl.}: uint32
|
||||
kprint("\n[Kernel] next_mmio_addr check: ")
|
||||
kprint_hex(uint64(next_mmio_addr))
|
||||
kprintln("")
|
||||
kprintln("\nNexus Sovereign Core v1.1 Starting...")
|
||||
kprintln("\nNexus Sovereign Core v1.1.1 Starting...")
|
||||
ion_pool_init()
|
||||
proc mm_init() {.importc, cdecl.}
|
||||
proc mm_enable_kernel_paging() {.importc, cdecl.}
|
||||
|
|
|
|||
|
|
@ -73,6 +73,8 @@ when not defined(RUMPK_KERNEL):
|
|||
discard syscall(0x100, 0)
|
||||
|
||||
proc pump_membrane_stack*() {.importc, cdecl.}
|
||||
proc membrane_init*() {.importc, cdecl.}
|
||||
proc ion_user_wait_multi*(mask: uint64): int32 {.importc, cdecl.}
|
||||
|
||||
proc pledge*(promises: uint64): int {.exportc, cdecl.} =
|
||||
return int(syscall(0x101, promises))
|
||||
|
|
@ -367,6 +369,7 @@ proc syscall_get_time_ns*(): uint64 {.exportc, cdecl.} =
|
|||
""".}
|
||||
return ticks
|
||||
|
||||
|
||||
proc syscall_get_random*(): uint32 {.exportc, cdecl.} =
|
||||
## Generate cryptographically strong random number for TCP ISN
|
||||
## Implementation: SipHash-2-4(MonolithKey, Time || CycleCount)
|
||||
|
|
|
|||
|
|
@ -13,10 +13,10 @@
|
|||
import ion_client
|
||||
# NOTE: Do NOT import ../../core/ion - it pulls in the KERNEL-ONLY 2MB memory pool!
|
||||
|
||||
proc debug_print(s: pointer, len: uint) {.importc: "debug_print", cdecl.}
|
||||
|
||||
proc console_write(s: pointer, len: csize_t) {.importc: "console_write", cdecl.}
|
||||
|
||||
proc glue_print(s: string) =
|
||||
debug_print(unsafeAddr s[0], uint(s.len))
|
||||
console_write(unsafeAddr s[0], csize_t(s.len))
|
||||
|
||||
# LwIP Imports
|
||||
{.passC: "-Icore/rumpk/vendor/lwip/src/include".}
|
||||
|
|
@ -66,7 +66,7 @@ type
|
|||
# Forward declarations for LwIP callbacks
|
||||
proc ion_linkoutput(netif: pointer, p: pointer): int32 {.exportc, cdecl.} =
|
||||
## Callback: LwIP -> Netif -> ION Ring
|
||||
# glue_print("[Membrane] Egress Packet\n")
|
||||
glue_print("[Membrane] Egress Packet\n")
|
||||
var pkt: IonPacket
|
||||
if not ion_user_alloc(addr pkt):
|
||||
return -1 # ERR_MEM
|
||||
|
|
@ -139,7 +139,7 @@ proc membrane_init*() {.exportc, cdecl.} =
|
|||
netif_set_default(&ni_static);
|
||||
netif_set_up(&ni_static);
|
||||
|
||||
// dhcp_start(&ni_static); // DISABLED: Nuking LwIP
|
||||
dhcp_start(&ni_static);
|
||||
|
||||
`g_netif` = &ni_static;
|
||||
""".}
|
||||
|
|
@ -148,13 +148,24 @@ proc membrane_init*() {.exportc, cdecl.} =
|
|||
|
||||
var last_notified_ip: uint32 = 0
|
||||
|
||||
# proc glue_print_hex(v: uint64) =
|
||||
# const hex_chars = "0123456789ABCDEF"
|
||||
# var buf: array[20, char]
|
||||
# buf[0] = '0'; buf[1] = 'x'
|
||||
# var val = v
|
||||
# for i in countdown(15, 0):
|
||||
# buf[2+i] = hex_chars[int(val and 0xF)]
|
||||
# val = val shr 4
|
||||
# buf[18] = '\n'; buf[19] = '\0'
|
||||
# buf[18] = '\n'; buf[19] = '\0'
|
||||
# console_write(addr buf[0], 20)
|
||||
|
||||
proc pump_membrane_stack*() {.exportc, cdecl.} =
|
||||
## The Pulse of the Membrane. Call frequently to handle timers and RX.
|
||||
if not ion_net_available(): return
|
||||
|
||||
let now = sys_now()
|
||||
# proc kprint_hex_ext(v: uint64) {.importc: "kprint_hex", cdecl.}
|
||||
# kprint_hex_ext(uint64(now)) # Debug: Print time (LOUD!)
|
||||
# glue_print("[Membrane] Time: ")
|
||||
# glue_print_hex(uint64(now))
|
||||
|
||||
# 3. Check for IP (Avoid continuous Nim string allocation/leak)
|
||||
var ip_addr: uint32
|
||||
|
|
@ -181,12 +192,14 @@ proc pump_membrane_stack*() {.exportc, cdecl.} =
|
|||
dhcp_fine_tmr()
|
||||
last_dhcp_fine = now
|
||||
if now - last_dhcp_coarse >= 60000:
|
||||
glue_print("[Membrane] DHCP Coarse Timer\n")
|
||||
dhcp_coarse_tmr()
|
||||
last_dhcp_coarse = now
|
||||
|
||||
# 2. RX Ingress
|
||||
var pkt: IonPacket
|
||||
while ion_net_rx(addr pkt):
|
||||
glue_print("[Membrane] Ingress Packet\n")
|
||||
# Pass to LwIP
|
||||
{.emit: """
|
||||
struct pbuf *p = pbuf_alloc(PBUF_RAW, `pkt`.len, PBUF_POOL);
|
||||
|
|
|
|||
Loading…
Reference in New Issue