summaryrefslogtreecommitdiff
path: root/src/kernel/proc/exec.cc
diff options
context:
space:
mode:
authorRichard Qin <richard.qin.x@gmail.com>2026-07-10 11:31:46 +0800
committerRichard Qin <richard.qin.x@gmail.com>2026-07-10 11:31:46 +0800
commite90b72ec3082588b296956730bd2930cf8d5d671 (patch)
tree36ff6916af9b4176ea5a9662219d11e721f0b691 /src/kernel/proc/exec.cc
parent1767d390fbf3d0c65389de46caf0b6d43ef3b6ad (diff)
downloadlume-e90b72ec3082588b296956730bd2930cf8d5d671.tar.gz
lume-e90b72ec3082588b296956730bd2930cf8d5d671.tar.xz
refactor: promote new architecture to repository root
Archive the deprecated implementation under lume-legacy, make the new kernel the default root-level build, and update repository entry points without changing kernel behavior.
Diffstat (limited to 'src/kernel/proc/exec.cc')
-rw-r--r--src/kernel/proc/exec.cc260
1 files changed, 0 insertions, 260 deletions
diff --git a/src/kernel/proc/exec.cc b/src/kernel/proc/exec.cc
deleted file mode 100644
index 8d8c467..0000000
--- a/src/kernel/proc/exec.cc
+++ /dev/null
@@ -1,260 +0,0 @@
-// SPDX-License-Identifier: GPL-2.0-or-later
-/*
- * Copyright (C) 2026 Richard QIn
- */
-#include "common/types.h"
-#include "kernel/riscv.h"
-#include "kernel/proc.h"
-#include "kernel/mm.h"
-#include "kernel/elf.h"
-#include "fs/fs.h"
-#include "lib/string.h"
-#include "drivers/uart.h"
-#include "kernel/trap.h"
-
-extern char trampoline[];
-
-// RAII: Page Table Resource Management
-class VmGuard
-{
-public:
- uint64 *pagetable = nullptr;
- uint64 sz = 0;
-
- VmGuard() : pagetable(VM::uvmcreate()) {}
-
- ~VmGuard()
- {
- if (pagetable)
- {
- VM::uvmfree(pagetable, sz);
- }
- }
-
- // Copying is prohibited
- VmGuard(const VmGuard &) = delete;
- VmGuard &operator=(const VmGuard &) = delete;
-
- // Submit resources: Ownership transfer, destructor no longer releases
- uint64 *commit()
- {
- uint64 *pt = pagetable;
- pagetable = nullptr;
- return pt;
- }
-};
-
-// RAII: Inode Lock Management
-class InodeGuard
-{
-public:
- Inode *ip;
- InodeGuard(Inode *i) : ip(i)
- {
- if (ip)
- VFS::ilock(ip);
- }
- ~InodeGuard()
- {
- if (ip)
- {
- VFS::iunlockput(ip); // Automatically unlock and release references
- }
- }
- // Copying is prohibited
- InodeGuard(const InodeGuard &) = delete;
- InodeGuard &operator=(const InodeGuard &) = delete;
-};
-
-// laod segment
-static int loadseg(uint64 *pagetable, uint64 va, Inode *ip, uint64 offset, uint64 sz)
-{
- for (uint64 i = 0; i < sz; i += PGSIZE)
- {
- uint64 pa = VM::walkaddr(pagetable, va + i);
- if (pa == 0)
- {
- Drivers::uart_puts("[Exec Debug] loadseg: walkaddr failed\n");
- return -1;
- }
-
- uint64 n = PGSIZE - (va + i) % PGSIZE;
- if (i + n > sz)
- n = sz - i;
-
- // Read physical address (isUser=0)
- if (ip->read((char *)(pa + (va + i) % PGSIZE), offset + i, n, 0) != (int)n)
- {
- Drivers::uart_puts("[Exec Debug] loadseg: read failed\n");
- return -1;
- }
- }
- return 0;
-}
-
-namespace Exec
-{
- int exec(char *path, char **argv)
- {
- // 1. Get Inode
- Inode *raw_ip = VFS::namei(path);
- if (!raw_ip)
- {
- Drivers::uart_puts("[Exec Debug] namei failed for path: ");
- Drivers::uart_puts(path);
- Drivers::uart_puts("\n");
- return -1;
- }
- InodeGuard iguard(raw_ip);
-
- // Get ELF head
- struct elfhdr elf;
- if (raw_ip->read((char *)&elf, 0, sizeof(elf), 0) != sizeof(elf))
- {
- Drivers::uart_puts("[Exec Debug] read elf header failed\n");
- return -1;
- }
- if (elf.magic != ELF_MAGIC)
- {
- Drivers::uart_puts("[Exec Debug] invalid elf magic\n");
- return -1;
- }
-
- // Create new pagetable
- VmGuard vm_guard;
- if (!vm_guard.pagetable)
- {
- Drivers::uart_puts("[Exec Debug] uvmcreate failed\n");
- return -1;
- }
-
- // Load Program Segment
- struct proghdr ph;
- for (int i = 0; i < elf.phnum; i++)
- {
- uint64 off = elf.phoff + i * sizeof(ph);
- if (raw_ip->read((char *)&ph, off, sizeof(ph), 0) != sizeof(ph))
- {
- Drivers::uart_puts("[Exec Debug] read proghdr failed\n");
- return -1;
- }
-
- if (ph.type != ELF_PROG_LOAD)
- continue;
- if (ph.memsz < ph.filesz)
- return -1;
- if (ph.vaddr + ph.memsz < ph.vaddr)
- return -1;
-
- uint64 sz1 = VM::uvmalloc(vm_guard.pagetable, vm_guard.sz, ph.vaddr + ph.memsz, PTE_W | PTE_X | PTE_R | PTE_U);
- if (sz1 == 0)
- {
- Drivers::uart_puts("[Exec Debug] uvmalloc failed (segment)\n");
- return -1;
- }
- vm_guard.sz = sz1;
-
- if (loadseg(vm_guard.pagetable, ph.vaddr, raw_ip, ph.off, ph.filesz) < 0)
- return -1;
- }
-
- // Prepare user stack
- uint64 sz = PGROUNDUP(vm_guard.sz);
-
- const int stack_data_pages = 16;
- const int stack_total_pages = stack_data_pages + 1;
-
- uint64 sz1 = VM::uvmalloc(vm_guard.pagetable, sz, sz + stack_total_pages * PGSIZE, PTE_W | PTE_R | PTE_U);
- if (sz1 == 0)
- {
- Drivers::uart_puts("[Exec Debug] uvmalloc failed (stack)\n");
- return -1;
- }
- vm_guard.sz = sz1;
-
- VM::uvmunmap(vm_guard.pagetable, sz, 1, 0);
-
- uint64 sp = sz1;
- uint64 stackbase = sp - stack_data_pages * PGSIZE;
- uint64 ustack[32];
- uint64 argc = 0;
-
- // Push parameter string
- for (; argv[argc]; argc++)
- {
- if (argc >= 31)
- return -1;
- sp -= strlen(argv[argc]) + 1;
- sp -= sp % 16;
- if (sp < stackbase)
- {
- Drivers::uart_puts("[Exec Debug] stack overflow (args)\n");
- return -1;
- }
-
- if (VM::copyout(vm_guard.pagetable, sp, argv[argc], strlen(argv[argc]) + 1) < 0)
- {
- Drivers::uart_puts("[Exec Debug] copyout arg string failed\n");
- return -1;
- }
- ustack[argc] = sp;
- }
- ustack[argc] = 0;
-
- // Push into parameter array
- sp -= (argc + 1) * sizeof(uint64);
- sp -= sp % 16;
- if (sp < stackbase)
- {
- Drivers::uart_puts("[Exec Debug] stack overflow (argv array)\n");
- return -1;
- }
- if (VM::copyout(vm_guard.pagetable, sp, (char *)ustack, (argc + 1) * sizeof(uint64)) < 0)
- {
- Drivers::uart_puts("[Exec Debug] copyout argv array failed\n");
- return -1;
- }
-
- // Commit Changes
- struct Proc *p = myproc();
- if (VM::mappages(vm_guard.pagetable, TRAPFRAME, PGSIZE, (uint64)p->tf, PTE_R | PTE_W) < 0)
- {
- Drivers::uart_puts("[Exec Debug] mappages TRAPFRAME failed\n");
- return -1;
- }
-
- uint64 oldsz = p->sz;
- uint64 *oldpagetable = p->pagetable;
-
- p->tf->a0 = argc;
- p->tf->a1 = sp;
- p->tf->sp = sp;
- p->tf->epc = elf.entry;
-
- char *s = path, *last = path;
- while (*s)
- {
- if (*s == '/')
- last = s + 1;
- s++;
- }
-
- size_t len = 0;
- while (last[len] && len < sizeof(p->name) - 1)
- {
- p->name[len] = last[len];
- len++;
- }
- p->name[len] = '\0';
-
- // change pagetable
- p->pagetable = vm_guard.commit();
- p->sz = vm_guard.sz;
-
- // release old pagetable
- VM::uvmfree(oldpagetable, oldsz);
- asm volatile("fence.i");
-
- return 0; // iguard unlocks and releases IP upon destruction
- }
-} \ No newline at end of file