Merge remote-tracking branch 'bpc/user-lib-bin' into merge-1228

# Conflicts:
#	kernel/src/arch/riscv32/compiler_rt.c
#	kernel/src/arch/riscv32/consts.rs
#	kernel/src/arch/riscv32/context.rs
#	kernel/src/arch/riscv32/io.rs
#	kernel/src/arch/riscv32/memory.rs
#	kernel/src/arch/riscv32/paging.rs
#	user/ucore-ulib/src/syscall.rs
master
WangRunji 6 years ago
commit 33eaded142

@ -138,8 +138,10 @@ fn log2(x: u16) -> usize {
log2_naive(x)
}
#[cfg(not(target_arch = "x86_64"))]
#[inline(always)]
fn log2_naive(mut x: u16) -> usize {
//a naive implement
assert_ne!(x, 0);
let mut pos = -1;
while x != 0 {
@ -153,6 +155,7 @@ fn log2_naive(mut x: u16) -> usize {
mod tests {
use super::*;
#[cfg(not(target_arch = "x86_64"))]
#[test]
fn log2_() {
for x in 1..=0xffff {

@ -3,7 +3,6 @@
//! Implemented for every architecture, used by OS.
use super::*;
use log::*;
#[cfg(test)]
pub use self::mock_page_table::MockPageTable;
pub use self::ext::*;

@ -108,7 +108,7 @@ impl<T: PageTable, M: SwapManager, S: Swapper> SwapExt<T, M, S> {
** @param addr: VirtAddr the target page's virtual address
*/
pub unsafe fn set_swappable<T2: InactivePageTable>(&mut self, pt: *mut T2, addr: VirtAddr){
let Self {ref mut page_table, ref mut swap_manager, ref mut swapper} = self;
let Self {ref mut page_table, ref mut swap_manager, ..} = self;
let targetpt = &mut *(pt);
let pttoken = {
info!("SET_SWAPPABLE: the target page table token is {:x?}, addr is {:x?}", targetpt.token(), addr);
@ -209,7 +209,7 @@ impl<T: PageTable, M: SwapManager, S: Swapper> SwapExt<T, M, S> {
** the error if failed
*/
fn swap_out<T2: InactivePageTable>(&mut self, frame: &Frame) -> Result<PhysAddr, SwapError> {
let Self {ref mut page_table, ref mut swap_manager, ref mut swapper} = self;
let Self {ref mut page_table, ref mut swapper, ..} = self;
let ret = unsafe{
let pt = &mut *(frame.get_page_table() as *mut T2);
pt.with(|| {
@ -296,7 +296,7 @@ impl<T: PageTable, M: SwapManager, S: Swapper> SwapExt<T, M, S> {
entry.set_present(true);
entry.update();
}
if(swapin){
if swapin {
unsafe {
self.set_swappable(pt, addr & 0xfffff000);
}

@ -69,6 +69,7 @@ impl<T: PartialEq> EventHub<T> {
}
self.timers.insert(i, timer);
}
#[allow(dead_code)]
pub fn get_time(&self) -> Time {
self.tick
}

@ -1,13 +1,12 @@
use alloc::boxed::Box;
use alloc::sync::Arc;
use alloc::vec::Vec;
use spin::Mutex;
use log::*;
use core::cell::UnsafeCell;
use crate::scheduler::Scheduler;
use crate::event_hub::EventHub;
struct Process {
#[allow(dead_code)]
id: Pid,
status: Status,
status_after_stop: Status,

@ -1,6 +1,5 @@
use alloc::boxed::Box;
use alloc::sync::Arc;
use spin::Mutex;
use log::*;
use core::cell::UnsafeCell;
use crate::process_manager::*;
@ -30,14 +29,12 @@ impl Processor {
}
pub unsafe fn init(&self, id: usize, context: Box<Context>, manager: Arc<ProcessManager>) {
unsafe {
*self.inner.get() = Some(ProcessorInner {
id,
proc: None,
loop_context: context,
manager,
});
}
*self.inner.get() = Some(ProcessorInner {
id,
proc: None,
loop_context: context,
manager,
});
}
fn inner(&self) -> &mut ProcessorInner {

@ -79,7 +79,7 @@ mod rr {
*rest == 0
}
fn set_priority(&mut self, pid: usize, priority: u8) {
fn set_priority(&mut self, _pid: usize, _priority: u8) {
}
fn move_to_head(&mut self, pid: usize) {

@ -7,14 +7,11 @@
//! - `new_kernel_context`: Construct a `Context` of the new kernel thread
use alloc::boxed::Box;
use alloc::collections::BTreeMap;
use core::marker::PhantomData;
use core::ptr;
use core::time::Duration;
use log::*;
use crate::processor::*;
use crate::process_manager::*;
use crate::scheduler::Scheduler;
#[linkage = "weak"]
#[no_mangle]
@ -26,7 +23,7 @@ fn processor() -> &'static Processor {
#[linkage = "weak"]
#[no_mangle]
/// Construct a `Context` of the new kernel thread
fn new_kernel_context(entry: extern fn(usize) -> !, arg: usize) -> Box<Context> {
fn new_kernel_context(_entry: extern fn(usize) -> !, _arg: usize) -> Box<Context> {
unimplemented!("thread: Please implement and export `new_kernel_context`")
}

6
kernel/Cargo.lock generated

@ -254,7 +254,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "simple-filesystem"
version = "0.0.1"
source = "git+https://github.com/wangrunji0408/SimpleFileSystem-Rust?branch=multi-thread#249383f7e3f195e0a8ce858f40394e9d5f7f58e0"
source = "git+https://github.com/benpigchu/SimpleFileSystem-Rust?branch=ucore-fs-enhance#b216da64ce4ee9cb24059478ffd4fa80ab8f30d2"
dependencies = [
"bit-vec 0.5.0 (git+https://github.com/AltSysrq/bit-vec.git)",
"spin 0.4.10 (registry+https://github.com/rust-lang/crates.io-index)",
@ -324,7 +324,7 @@ dependencies = [
"pc-keyboard 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)",
"raw-cpuid 6.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"riscv 0.3.0 (git+https://github.com/riscv-and-rust-and-decaf/riscv)",
"simple-filesystem 0.0.1 (git+https://github.com/wangrunji0408/SimpleFileSystem-Rust?branch=multi-thread)",
"simple-filesystem 0.0.1 (git+https://github.com/benpigchu/SimpleFileSystem-Rust?branch=ucore-fs-enhance)",
"spin 0.4.10 (registry+https://github.com/rust-lang/crates.io-index)",
"uart_16550 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"ucore-memory 0.1.0",
@ -467,7 +467,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
"checksum rustc_version 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "138e3e0acb6c9fb258b19b67cb8abd63c00679d2851805ea151465464fe9030a"
"checksum semver 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)" = "1d7eb9ef2c18661902cc47e535f9bc51b78acd254da71d375c2f6720d9a40403"
"checksum semver-parser 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "388a1df253eca08550bef6c72392cfe7c30914bf41df5269b68cbd6ff8f570a3"
"checksum simple-filesystem 0.0.1 (git+https://github.com/wangrunji0408/SimpleFileSystem-Rust?branch=multi-thread)" = "<none>"
"checksum simple-filesystem 0.0.1 (git+https://github.com/benpigchu/SimpleFileSystem-Rust?branch=ucore-fs-enhance)" = "<none>"
"checksum skeptic 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "061203a849117b0f7090baf8157aa91dac30545208fbb85166ac58b4ca33d89c"
"checksum spin 0.4.10 (registry+https://github.com/rust-lang/crates.io-index)" = "ceac490aa12c567115b40b7b7fceca03a6c9d53d5defea066123debc83c5dc1f"
"checksum static_assertions 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "389ce475f424f267dbed6479cbd8f126c5e1afb053b0acdaa019c74305fc65d1"

@ -56,6 +56,9 @@ aarch64 = { git = "https://github.com/equation314/aarch64" }
atags = { path = "../crate/atags" }
bcm2837 = { path = "../crate/bcm2837", optional = true }
[patch.'https://github.com/wangrunji0408/SimpleFileSystem-Rust']
simple-filesystem = { git = "https://github.com/benpigchu/SimpleFileSystem-Rust", branch = "ucore-fs-enhance" }
[package.metadata.bootimage]
default-target = "x86_64-blog_os.json"
output = "target/x86_64-blog_os/bootimage.bin"

@ -22,6 +22,7 @@ fn main() {
.file("src/arch/riscv32/compiler_rt.c")
.flag("-march=rv32ia")
.flag("-mabi=ilp32")
.flag("-Wno-builtin-declaration-mismatch")
.compile("atomic_rt");
if let Ok(file_path) = gen_sfsimg_asm() {
cc::Build::new()

@ -1,6 +1,5 @@
use crate::arch::interrupt::TrapFrame;
use bcm2837::interrupt::Controller;
use log::*;
pub use bcm2837::interrupt::Interrupt;

@ -5,7 +5,7 @@ use ucore_memory::PAGE_SIZE;
use atags::atags::Atags;
use aarch64::{barrier, regs::*, addr::*};
use aarch64::paging::{PhysFrame as Frame, memory_attribute::*};
use crate::memory::{FRAME_ALLOCATOR, init_heap, MemoryArea, MemoryAttr, MemorySet, Linear};
use crate::memory::{FRAME_ALLOCATOR, init_heap, MemoryAttr, MemorySet, Linear};
/// Memory initialization.
pub fn init() {

@ -1,8 +1,6 @@
//! Page table implementations for aarch64.
use ucore_memory::memory_set::*;
use ucore_memory::PAGE_SIZE;
use ucore_memory::paging::*;
use aarch64::asm::{tlb_invalidate, tlb_invalidate_all, flush_icache_all, ttbr_el1_read, ttbr_el1_write};
use aarch64::asm::{tlb_invalidate, tlb_invalidate_all, ttbr_el1_read, ttbr_el1_write};
use aarch64::{PhysAddr, VirtAddr};
use aarch64::paging::{Mapper, PageTable as Aarch64PageTable, PageTableEntry, PageTableFlags as EF, RecursivePageTable};
use aarch64::paging::{FrameAllocator, FrameDeallocator, Page, PhysFrame as Frame, Size4KiB, Size2MiB, Size1GiB};

@ -153,7 +153,7 @@ impl Context {
/// Pop all callee-saved registers, then return to the target.
#[naked]
#[inline(never)]
pub unsafe extern fn switch(&mut self, target: &mut Self) {
pub unsafe extern fn switch(&mut self, _target: &mut Self) {
#[cfg(target_arch = "riscv32")]
asm!(r"
.equ XLENB, 4
@ -256,7 +256,7 @@ impl Context {
* @retval:
* a Context struct with the pointer to the kernel stack top - 1 as its only element
*/
pub unsafe fn new_user_thread(entry_addr: usize, ustack_top: usize, kstack_top: usize, is32: bool, cr3: usize) -> Self {
pub unsafe fn new_user_thread(entry_addr: usize, ustack_top: usize, kstack_top: usize, _is32: bool, cr3: usize) -> Self {
InitStack {
context: ContextData::new(cr3),
tf: TrapFrame::new_user_thread(entry_addr, ustack_top),

@ -1,6 +1,5 @@
use crate::consts::MAX_CPU_NUM;
use core::ptr::{read_volatile, write_volatile};
use crate::memory::*;
static mut STARTED: [bool; MAX_CPU_NUM] = [false; MAX_CPU_NUM];

@ -12,7 +12,6 @@ use riscv::register::{
};
use riscv::register::{mcause, mepc, sie, mie};
pub use self::context::*;
use crate::memory::{MemorySet, InactivePageTable0};
use log::*;
#[path = "context.rs"]

@ -1,8 +1,8 @@
use core::{slice, mem};
use core::mem;
use riscv::{addr::*, register::sstatus};
use ucore_memory::PAGE_SIZE;
use log::*;
use crate::memory::{active_table, FRAME_ALLOCATOR, init_heap, MemoryArea, MemoryAttr, MemorySet, MEMORY_ALLOCATOR, Linear};
use crate::memory::{FRAME_ALLOCATOR, init_heap, MemoryAttr, MemorySet, Linear};
use crate::consts::{MEMORY_OFFSET, MEMORY_END, KERN_VA_BASE};
use riscv::register::satp;
@ -98,6 +98,7 @@ pub unsafe fn clear_bss() {
}
// Symbols provided by linker script
#[allow(dead_code)]
extern {
fn stext();
fn etext();

@ -20,7 +20,7 @@ pub extern fn rust_main(hartid: usize, dtb: usize, hart_mask: usize, functions:
while unsafe { !cpu::has_started(hartid) } { }
println!("Hello RISCV! in hart {}, dtb @ {:#x}, functions @ {:#x}", hartid, dtb, functions);
others_main();
unreachable!();
//other_main -> !
}
unsafe { memory::clear_bss(); }

@ -6,8 +6,6 @@ use riscv::asm::{sfence_vma, sfence_vma_all};
use riscv::paging::{Mapper, PageTable as RvPageTable, PageTableEntry, PageTableFlags as EF, RecursivePageTable};
use riscv::paging::{FrameAllocator, FrameDeallocator};
use riscv::register::satp;
use ucore_memory::memory_set::*;
use ucore_memory::PAGE_SIZE;
use ucore_memory::paging::*;
use log::*;
#[cfg(target_arch = "riscv32")]
@ -51,7 +49,7 @@ impl PageTable for ActivePageTable {
*/
fn unmap(&mut self, addr: usize) {
let page = Page::of_addr(VirtAddr::new(addr));
let (frame, flush) = self.0.unmap(page).unwrap();
let (_, flush) = self.0.unmap(page).unwrap();
flush.flush();
}
@ -217,7 +215,7 @@ impl Entry for PageEntry {
fn execute(&self) -> bool { self.0.flags().contains(EF::EXECUTABLE) }
fn set_execute(&mut self, value: bool) { self.0.flags_mut().set(EF::EXECUTABLE, value); }
fn mmio(&self) -> bool { false }
fn set_mmio(&mut self, value: bool) { }
fn set_mmio(&mut self, _value: bool) { }
}
#[derive(Debug)]

@ -18,7 +18,7 @@ pub fn id() -> usize {
pub fn send_ipi(cpu_id: usize) {
let mut lapic = unsafe { XApic::new(0xffffff00_fee00000) };
unsafe { lapic.send_ipi(cpu_id as u8, 0x30); } // TODO: Find a IPI trap num
lapic.send_ipi(cpu_id as u8, 0x30); // TODO: Find a IPI trap num
}
pub fn init() {

@ -88,7 +88,7 @@ impl IDE {
}
// ???
let mut data = [0; SECTOR_SIZE];
let data = [0; SECTOR_SIZE];
asm!("rep insl" :: "{dx}"(self.base + ISA_DATA), "{rdi}"(data.as_ptr()), "{cx}"(SECTOR_SIZE) : "rdi" : "volatile");
}
}

@ -25,7 +25,7 @@ pub fn receive() -> Option<char> {
if let Some(key) = keyboard.process_keyevent(key_event) {
match key {
DecodedKey::Unicode(character) => return Some(character),
DecodedKey::RawKey(key) => {}, // TODO: handle RawKey from keyboard
DecodedKey::RawKey(_key) => {}, // TODO: handle RawKey from keyboard
}
}
}

@ -1,6 +1,5 @@
// Copy from Redox
use core::fmt::{self, Write};
use x86_64::instructions::port::Port;
use spin::Mutex;
use uart_16550::SerialPort;
@ -27,7 +26,7 @@ impl SerialRead for SerialPort {
fn receive(&mut self) -> u8 {
unsafe {
let ports = self as *mut _ as *mut [Port<u8>; 6];
let line_sts = &(*ports)[5];
let _line_sts = &(*ports)[5];
let data = &(*ports)[0];
data.read()
}

@ -1,7 +1,5 @@
use alloc::boxed::Box;
use crate::consts::MAX_CPU_NUM;
use core::fmt;
use core::fmt::Debug;
use spin::{Mutex, MutexGuard, Once};
use x86_64::{PrivilegeLevel, VirtAddr};
use x86_64::structures::gdt::*;

@ -6,7 +6,7 @@ pub fn init() {
}
lazy_static! {
static ref IDT: Idt = {
static ref IDT: InterruptDescriptorTable = {
use crate::arch::interrupt::consts::*;
use crate::arch::gdt::DOUBLE_FAULT_IST_INDEX;
use x86_64::PrivilegeLevel;
@ -21,10 +21,10 @@ lazy_static! {
let ring3 = [T_SWITCH_TOK, T_SYSCALL, T_SYSCALL32];
let mut idt = Idt::new();
let entries = unsafe{ &mut *(&mut idt as *mut _ as *mut [IdtEntry<HandlerFunc>; 256]) };
let mut idt = InterruptDescriptorTable::new();
let entries = unsafe{ &mut *(&mut idt as *mut _ as *mut [Entry<HandlerFunc>; 256]) };
for i in 0..256 {
let mut opt = entries[i].set_handler_fn(unsafe { transmute(__vectors[i]) });
let opt = entries[i].set_handler_fn(unsafe { transmute(__vectors[i]) });
if ring3.contains(&(i as u8)) {
opt.set_privilege_level(PrivilegeLevel::Ring3);
opt.disable_interrupts(false);

@ -43,7 +43,7 @@ pub fn enable_irq(irq: u8) {
}
#[inline(always)]
pub fn ack(irq: u8) {
pub fn ack(_irq: u8) {
let mut lapic = unsafe { XApic::new(KERNEL_OFFSET + LAPIC_ADDR) };
lapic.eoi();
}

@ -119,7 +119,7 @@ impl Context {
/// Pop all callee-saved registers, then return to the target.
#[naked]
#[inline(never)]
pub unsafe extern fn switch(&mut self, target: &mut Self) {
pub unsafe extern fn switch(&mut self, _target: &mut Self) {
asm!(
"
// push rip (by caller)

@ -3,7 +3,6 @@ use crate::consts::KERNEL_OFFSET;
// Depends on kernel
use crate::memory::{FRAME_ALLOCATOR, init_heap, active_table};
use super::{BootInfo, MemoryRegionType};
use ucore_memory::PAGE_SIZE;
use ucore_memory::paging::*;
use once::*;
use log::*;

@ -1,7 +1,6 @@
use bootloader::bootinfo::{BootInfo, MemoryRegionType};
use core::sync::atomic::*;
use log::*;
use crate::consts::KERNEL_OFFSET;
pub mod driver;
pub mod cpu;

@ -1,16 +1,11 @@
// Depends on kernel
use crate::memory::{active_table, alloc_frame, dealloc_frame};
use spin::{Mutex, MutexGuard};
use ucore_memory::cow::CowExt;
use ucore_memory::memory_set::*;
use ucore_memory::PAGE_SIZE;
use ucore_memory::paging::*;
use x86_64::instructions::tlb;
use x86_64::PhysAddr;
use x86_64::registers::control::{Cr3, Cr3Flags};
use x86_64::structures::paging::{Mapper, PageTable as x86PageTable, PageTableEntry, PageTableFlags as EF, RecursivePageTable};
use x86_64::structures::paging::{FrameAllocator, FrameDeallocator, Page, PageRange, PhysFrame as Frame, Size4KiB};
use x86_64::ux::u9;
use log::*;
pub trait PageExt {
@ -51,7 +46,7 @@ impl PageTable for ActivePageTable {
}
fn unmap(&mut self, addr: usize) {
let (frame, flush) = self.0.unmap(Page::of_addr(addr)).unwrap();
let (_, flush) = self.0.unmap(Page::of_addr(addr)).unwrap();
flush.flush();
}
@ -117,7 +112,7 @@ impl Entry for PageEntry {
fn execute(&self) -> bool { !self.0.flags().contains(EF::NO_EXECUTE) }
fn set_execute(&mut self, value: bool) { self.as_flags().set(EF::NO_EXECUTE, !value); }
fn mmio(&self) -> bool { false }
fn set_mmio(&mut self, value: bool) { }
fn set_mmio(&mut self, _value: bool) { }
}
fn get_entry_ptr(addr: usize, level: u8) -> *mut PageEntry {
@ -152,7 +147,7 @@ impl InactivePageTable for InactivePageTable0 {
}
fn map_kernel(&mut self) {
let mut table = unsafe { &mut *(0xffffffff_fffff000 as *mut x86PageTable) };
let table = unsafe { &mut *(0xffffffff_fffff000 as *mut x86PageTable) };
// Kernel at 0xffff_ff00_0000_0000
// Kernel stack at 0x0000_57ac_0000_0000 (defined in bootloader crate)
let e510 = table[510].clone();

@ -1,7 +1,6 @@
use simple_filesystem::*;
use alloc::{boxed::Box, sync::Arc, string::String, collections::VecDeque, vec::Vec};
use core::any::Any;
use core::slice;
use lazy_static::lazy_static;
#[cfg(target_arch = "x86_64")]
use crate::arch::driver::ide;
@ -27,8 +26,10 @@ lazy_static! {
};
}
#[cfg(not(target_arch = "x86_64"))]
struct MemBuf(&'static [u8]);
#[cfg(not(target_arch = "x86_64"))]
impl MemBuf {
unsafe fn new(begin: unsafe extern fn(), end: unsafe extern fn()) -> Self {
use core::slice;
@ -36,6 +37,7 @@ impl MemBuf {
}
}
#[cfg(not(target_arch = "x86_64"))]
impl Device for MemBuf {
fn read_at(&mut self, offset: usize, buf: &mut [u8]) -> Option<usize> {
let slice = self.0;
@ -43,7 +45,7 @@ impl Device for MemBuf {
buf[..len].copy_from_slice(&slice[offset..offset + len]);
Some(len)
}
fn write_at(&mut self, offset: usize, buf: &[u8]) -> Option<usize> {
fn write_at(&mut self, _offset: usize, _buf: &[u8]) -> Option<usize> {
None
}
}
@ -52,11 +54,13 @@ impl Device for MemBuf {
impl BlockedDevice for ide::IDE {
const BLOCK_SIZE_LOG2: u8 = 9;
fn read_at(&mut self, block_id: usize, buf: &mut [u8]) -> bool {
use core::slice;
assert!(buf.len() >= ide::BLOCK_SIZE);
let buf = unsafe { slice::from_raw_parts_mut(buf.as_ptr() as *mut u32, ide::BLOCK_SIZE / 4) };
self.read(block_id as u64, 1, buf).is_ok()
}
fn write_at(&mut self, block_id: usize, buf: &[u8]) -> bool {
use core::slice;
assert!(buf.len() >= ide::BLOCK_SIZE);
let buf = unsafe { slice::from_raw_parts(buf.as_ptr() as *mut u32, ide::BLOCK_SIZE / 4) };
self.write(block_id as u64, 1, buf).is_ok()
@ -104,35 +108,36 @@ lazy_static! {
// TODO: better way to provide default impl?
macro_rules! impl_inode {
() => {
fn info(&self) -> Result<FileInfo> { unimplemented!() }
fn sync(&self) -> Result<()> { unimplemented!() }
fn resize(&self, len: usize) -> Result<()> { unimplemented!() }
fn create(&self, name: &str, type_: FileType) -> Result<Arc<INode>> { unimplemented!() }
fn unlink(&self, name: &str) -> Result<()> { unimplemented!() }
fn link(&self, name: &str, other: &Arc<INode>) -> Result<()> { unimplemented!() }
fn rename(&self, old_name: &str, new_name: &str) -> Result<()> { unimplemented!() }
fn move_(&self, old_name: &str, target: &Arc<INode>, new_name: &str) -> Result<()> { unimplemented!() }
fn find(&self, name: &str) -> Result<Arc<INode>> { unimplemented!() }
fn get_entry(&self, id: usize) -> Result<String> { unimplemented!() }
fn info(&self) -> Result<FileInfo> { Err(FsError::NotSupported) }
fn sync(&self) -> Result<()> { Ok(()) }
fn resize(&self, _len: usize) -> Result<()> { Err(FsError::NotSupported) }
fn create(&self, _name: &str, _type_: FileType) -> Result<Arc<INode>> { Err(FsError::NotDir) }
fn unlink(&self, _name: &str) -> Result<()> { Err(FsError::NotDir) }
fn link(&self, _name: &str, _other: &Arc<INode>) -> Result<()> { Err(FsError::NotDir) }
fn rename(&self, _old_name: &str, _new_name: &str) -> Result<()> { Err(FsError::NotDir) }
fn move_(&self, _old_name: &str, _target: &Arc<INode>, _new_name: &str) -> Result<()> { Err(FsError::NotDir) }
fn find(&self, _name: &str) -> Result<Arc<INode>> { Err(FsError::NotDir) }
fn get_entry(&self, _id: usize) -> Result<String> { Err(FsError::NotDir) }
fn fs(&self) -> Arc<FileSystem> { unimplemented!() }
fn as_any_ref(&self) -> &Any { self }
};
}
impl INode for Stdin {
fn read_at(&self, offset: usize, buf: &mut [u8]) -> Result<usize> {
fn read_at(&self, _offset: usize, buf: &mut [u8]) -> Result<usize> {
buf[0] = self.pop() as u8;
Ok(1)
}
fn write_at(&self, offset: usize, buf: &[u8]) -> Result<usize> { unimplemented!() }
fn write_at(&self, _offset: usize, _buf: &[u8]) -> Result<usize> { unimplemented!() }
impl_inode!();
}
impl INode for Stdout {
fn read_at(&self, offset: usize, buf: &mut [u8]) -> Result<usize> { unimplemented!() }
fn write_at(&self, offset: usize, buf: &[u8]) -> Result<usize> {
fn read_at(&self, _offset: usize, _buf: &mut [u8]) -> Result<usize> { unimplemented!() }
fn write_at(&self, _offset: usize, buf: &[u8]) -> Result<usize> {
use core::str;
let s = str::from_utf8(buf).map_err(|_| ())?;
//we do not care the utf-8 things, we just want to print it!
let s = unsafe{ str::from_utf8_unchecked(buf) };
print!("{}", s);
Ok(buf.len())
}

@ -44,22 +44,21 @@ macro_rules! with_color {
fn print_in_color(args: fmt::Arguments, color: Color) {
use crate::arch::io;
let mutex = log_mutex.lock();
let _guard = log_mutex.lock();
io::putfmt(with_color!(args, color));
}
pub fn print(args: fmt::Arguments) {
use crate::arch::io;
let mutex = log_mutex.lock();
let _guard = log_mutex.lock();
io::putfmt(args);
}
struct SimpleLogger;
impl Log for SimpleLogger {
fn enabled(&self, metadata: &Metadata) -> bool {
true
// metadata.level() <= Level::Info
fn enabled(&self, _metadata: &Metadata) -> bool {
true
}
fn log(&self, record: &Record) {
static DISABLED_TARGET: &[&str] = &[

@ -2,4 +2,5 @@
#![cfg_attr(not(test), no_main)] // disable all Rust-level entry points
#![cfg_attr(test, allow(dead_code, unused_macros, unused_imports))]
#[allow(unused_imports)]
use ucore;

@ -2,13 +2,11 @@ pub use crate::arch::paging::*;
use bit_allocator::BitAlloc;
use crate::consts::MEMORY_OFFSET;
use super::HEAP_ALLOCATOR;
use ucore_memory::{*, paging::PageTable};
use ucore_memory::*;
use ucore_memory::cow::CowExt;
pub use ucore_memory::memory_set::{MemoryArea, MemoryAttr, handler::*};
use ucore_memory::swap::*;
use crate::process::{process};
use crate::sync::{SpinNoIrqLock, SpinNoIrq, MutexGuard};
use alloc::collections::VecDeque;
use lazy_static::*;
use log::*;
use linked_list_allocator::LockedHeap;

@ -4,10 +4,10 @@ use log::*;
use simple_filesystem::file::File;
use spin::Mutex;
use ucore_process::Context;
use xmas_elf::{ElfFile, header, program::{Flags, ProgramHeader, SegmentData, Type}};
use xmas_elf::{ElfFile, header, program::{Flags, Type}};
use crate::arch::interrupt::{Context as ArchContext, TrapFrame};
use crate::memory::{ByFrame, Delay, FrameAllocator, GlobalFrameAlloc, KernelStack, MemoryArea, MemoryAttr, MemorySet};
use crate::memory::{ByFrame, GlobalFrameAlloc, KernelStack, MemoryAttr, MemorySet};
// TODO: avoid pub
pub struct Process {
@ -110,7 +110,7 @@ impl Process {
pub fn fork(&self, tf: &TrapFrame) -> Box<Context> {
info!("COME into fork!");
// Clone memory set, make a new page table
let mut memory_set = self.memory_set.clone();
let memory_set = self.memory_set.clone();
info!("finish mmset clone in fork!");
// MMU: copy data to the new space
@ -149,7 +149,6 @@ unsafe fn push_slice<T: Copy>(mut sp: usize, vs: &[T]) -> usize {
unsafe fn push_args_at_stack<'a, Iter>(args: Iter, stack_top: usize) -> usize
where Iter: Iterator<Item=&'a str>
{
use core::{ptr, slice};
let mut sp = stack_top;
let mut argv = Vec::new();
for arg in args {

@ -1,11 +1,8 @@
use spin::Mutex;
pub use self::context::Process;
pub use ucore_process::*;
use crate::consts::{MAX_CPU_NUM, MAX_PROCESS_NUM};
use crate::arch::cpu;
use alloc::{boxed::Box, sync::Arc, vec::Vec};
use crate::sync::Condvar;
use core::sync::atomic::*;
use alloc::{boxed::Box, sync::Arc};
use log::*;
pub mod context;

@ -1,7 +1,6 @@
//! Kernel shell
use alloc::string::String;
use alloc::vec::Vec;
use crate::fs::{ROOT_INODE, INodeExt};
use crate::process::*;

@ -48,6 +48,7 @@
//! Dining_Philosophers --> Monitor
//! end
//! ```
#![allow(dead_code)]
pub use self::condvar::*;
pub use self::mutex::*;

@ -1,6 +1,6 @@
//! System call
use simple_filesystem::{INode, file::File, FileInfo, FileType};
use simple_filesystem::{INode, file::File, FileInfo, FileType, FsError};
use core::{slice, str};
use alloc::{sync::Arc, vec::Vec, string::String};
use spin::Mutex;
@ -53,7 +53,7 @@ pub fn syscall(id: usize, args: [usize; 6], tf: &mut TrapFrame) -> isize {
};
match ret {
Ok(code) => code,
Err(_) => -1,
Err(err) => -(err as isize),
}
}
@ -96,7 +96,7 @@ fn sys_close(fd: usize) -> SysResult {
info!("close: fd: {:?}", fd);
match process().files.remove(&fd) {
Some(_) => Ok(0),
None => Err(SysError::InvalidFile),
None => Err(SysError::Inval),
}
}
@ -118,11 +118,11 @@ fn sys_getdirentry(fd: usize, dentry_ptr: *mut DirEntry) -> SysResult {
let file = get_file(fd)?;
let dentry = unsafe { &mut *dentry_ptr };
if !dentry.check() {
return Err(SysError::InvalidArgument);
return Err(SysError::Inval);
}
let info = file.lock().info()?;
if info.type_ != FileType::Dir || info.size <= dentry.entry_id() {
return Err(SysError::InvalidArgument);
return Err(SysError::Inval);
}
let name = file.lock().get_entry(dentry.entry_id())?;
dentry.set_name(name.as_str());
@ -133,7 +133,7 @@ fn sys_dup(fd1: usize, fd2: usize) -> SysResult {
info!("dup: {} {}", fd1, fd2);
let file = get_file(fd1)?;
if process().files.contains_key(&fd2) {
return Err(SysError::InvalidFile);
return Err(SysError::Inval);
}
process().files.insert(fd2, file.clone());
Ok(0)
@ -141,7 +141,7 @@ fn sys_dup(fd1: usize, fd2: usize) -> SysResult {
/// Fork the current process. Return the child's PID.
fn sys_fork(tf: &TrapFrame) -> SysResult {
let mut context = process().fork(tf);
let context = process().fork(tf);
//memory_set_map_swappable(context.get_memory_set_mut());
let pid = processor().manager().add(context, thread::current().id());
//memory_set_map_swappable(processor.get_context_mut(pid).get_memory_set_mut());
@ -198,6 +198,9 @@ fn sys_exec(name: *const u8, argc: usize, argv: *const *const u8, tf: &mut TrapF
.collect()
};
if args.len() <= 0 {
return Err(SysError::Inval);
}
// Read program file
let path = args[0].as_str();
let inode = crate::fs::ROOT_INODE.lookup(path)?;
@ -278,7 +281,7 @@ fn sys_putc(c: char) -> SysResult {
}
fn get_file(fd: usize) -> Result<&'static Arc<Mutex<File>>, SysError> {
process().files.get(&fd).ok_or(SysError::InvalidFile)
process().files.get(&fd).ok_or(SysError::Inval)
}
pub type SysResult = Result<isize, SysError>;
@ -286,14 +289,41 @@ pub type SysResult = Result<isize, SysError>;
#[repr(isize)]
#[derive(Debug)]
pub enum SysError {
VfsError,
InvalidFile,
InvalidArgument,
// ucore compatible error code
// note that ucore_plus use another error code table, which is a modified version of the ones used in linux
// name conversion E_XXXXX -> SysError::Xxxxx
// see https://github.com/oscourse-tsinghua/ucore_os_lab/blob/master/labcodes/lab8/libs/error.h
// we only add current used errors here
Inval = 3,// Invalid argument, also Invaild fd number.
Nomem = 4,// Out of memory, also used as no device space in ucore
Noent = 16,// No such file or directory
Isdir = 17,// Fd is a directory
Notdir = 18,// Fd is not a directory
Xdev = 19,// Cross-device link
Unimp = 20,// Not implemented
Exists = 23,// File exists
Notempty = 24,// Directory is not empty
#[allow(dead_code)]
Unspcified = 1,// A really really unknown error.
}
impl From<()> for SysError {
fn from(_: ()) -> Self {
SysError::VfsError
impl From<FsError> for SysError {
fn from(error: FsError) -> Self {
match error {
FsError::NotSupported => SysError::Unimp,
FsError::NotFile => SysError::Isdir,
FsError::IsDir => SysError::Isdir,
FsError::NotDir => SysError::Notdir,
FsError::EntryNotFound => SysError::Noent,
FsError::EntryExist => SysError::Exists,
FsError::NotSameFs => SysError::Xdev,
FsError::InvalidParam => SysError::Inval,
FsError::NoDeviceSpace => SysError::Nomem,
FsError::DirRemoved => SysError::Noent,
FsError::DirNotEmpty => SysError::Notempty,
FsError::WrongFs => SysError::Inval,
}
}
}
@ -374,7 +404,10 @@ impl From<FileInfo> for Stat {
mode: match info.type_ {
FileType::File => StatMode::FILE,
FileType::Dir => StatMode::DIR,
_ => StatMode::NULL,
// _ => StatMode::NULL,
//Note: we should mark FileType as #[non_exhaustive]
// but it is currently not implemented for enum
// see rust-lang/rust#44109
},
nlinks: info.nlinks as u32,
blocks: info.blocks as u32,

@ -1,5 +1,3 @@
use core::fmt::Debug;
/// Convert C string to Rust string
pub unsafe fn from_cstr(s: *const u8) -> &'static str {
use core::{str, slice};

@ -0,0 +1,115 @@
#![no_std]
#![no_main]
#[macro_use]
extern crate ucore_ulib;
use ucore_ulib::io::getc;
use ucore_ulib::syscall::{sys_exec, sys_fork, sys_wait};
pub fn get_line(buffer: &mut [u8]) -> usize {
let mut pos: usize = 0;
loop {
let ret = getc();
match ret {
None => break,
Some(byte) => {
let c = byte as char;
match c {
'\u{8}' /* '\b' */ => {
if pos > 0 {
print!("\u{8} \u{8}");
pos-=1;
}
}
' '...'\u{7e}' => {
if pos<buffer.len() {
buffer[pos]=byte;
}
pos+=1;
print!("{}", c);
}
'\n' | '\r' => {
print!("\n");
break;
}
_ => {}
}
}
}
}
pos
}
const BUFFER_SIZE: usize = 4096;
// IMPORTANT: Must define main() like this
#[no_mangle]
pub fn main() -> i32 {
use core::mem::uninitialized;
let mut buf: [u8; BUFFER_SIZE] = unsafe { uninitialized() };
println!("Rust user shell");
loop {
print!(">> ");
let len = get_line(&mut buf);
if len > BUFFER_SIZE {
println!("Command is too long!");
} else {
let cmd = &buf[..len];
let mut parsed: [u8; BUFFER_SIZE + 1] = unsafe { uninitialized() };
let mut offset: [usize; BUFFER_SIZE + 1] = unsafe { uninitialized() };
let mut start: usize = 0;
let mut pos: usize = 0;
let mut is_word = false;
let mut parsed_pos: usize = 0;
let mut offset_pos: usize = 0;
loop {
if pos >= cmd.len() {
if is_word {
offset[offset_pos] = parsed_pos;
offset_pos += 1;
parsed[parsed_pos..parsed_pos + pos - start]
.copy_from_slice(&cmd[start..pos]);
parsed_pos += pos - start;
parsed[parsed_pos] = 0;
// parsed_pos+=1;
}
break;
}
if cmd[pos] == (' ' as u8) {
if is_word {
is_word = false;
offset[offset_pos] = parsed_pos;
offset_pos += 1;
parsed[parsed_pos..parsed_pos + pos - start]
.copy_from_slice(&cmd[start..pos]);
parsed_pos += pos - start;
parsed[parsed_pos] = 0;
parsed_pos += 1;
}
} else {
if !is_word {
is_word = true;
start = pos;
}
}
pos += 1;
}
if offset_pos > 0 {
let pid = sys_fork();
if pid == 0 {
let mut ptrs: [*const u8; BUFFER_SIZE] = unsafe { uninitialized() };
for i in 0..offset_pos {
ptrs[i] = unsafe { parsed.as_ptr().offset(offset[i] as isize) };
}
return sys_exec(parsed.as_ptr(), offset_pos, ptrs.as_ptr());
} else if pid < 0 {
panic!("pid<0")
} else {
let mut code: i32 = unsafe { uninitialized() };
sys_wait(pid as usize, &mut code as *mut i32);
println!("\n[Process exited with code {}]", code);
}
}
}
}
}

@ -0,0 +1,76 @@
use core::fmt::{self, Write};
use core::option::Option;
use crate::syscall::{sys_write, sys_read, sys_putc};
pub const STDIN: usize=0;
pub const STDOUT: usize=1;
#[macro_export]
macro_rules! print {
($($arg:tt)*) => ({
$crate::io::print(format_args!($($arg)*));
});
}
#[macro_export]
macro_rules! println {
($fmt:expr) => (print!(concat!($fmt, "\n")));
($fmt:expr, $($arg:tt)*) => (print!(concat!($fmt, "\n"), $($arg)*));
}
pub fn print(args: fmt::Arguments) {
StdOut.write_fmt(args).unwrap();
}
pub fn print_putc(args: fmt::Arguments) {
SysPutc.write_fmt(args).unwrap();
}
pub fn getc() -> Option<u8>{
use core::mem::uninitialized;
let mut c:[u8;1] = unsafe { uninitialized() };
let ret=sys_read(STDIN,c.as_mut_ptr(),1);
match ret {
1 => Some(c[0]),
0 => None,
_ => panic!(),
}
}
pub fn putc(c:u8){
sys_putc(c);
}
struct StdOut;
struct SysPutc;
impl fmt::Write for StdOut {
fn write_str(&mut self, s: &str) -> fmt::Result {
if sys_write(STDOUT, s.as_ptr(), s.len()) >= 0 {
Ok(())
} else {
Err(fmt::Error::default())
}
}
}
impl fmt::Write for SysPutc {
fn write_str(&mut self, s: &str) -> fmt::Result {
for c in s.bytes() {
sys_putc(c);
}
Ok(())
}
}
/* VFS flags */
// TODO: use bitflags
// flags for open: choose one of these
pub const O_RDONLY: usize = 0; // open for reading only
pub const O_WRONLY: usize = 1; // open for writing only
pub const O_RDWR: usize = 2; // open for reading and writing
// then or in any of these:
pub const O_CREAT: usize = 0x00000004; // create file if it does not exist
pub const O_EXCL: usize = 0x00000008; // error if O_CREAT and the file exists
pub const O_TRUNC: usize = 0x00000010; // truncate file upon open
pub const O_APPEND: usize = 0x00000020; // append on each write

@ -1,12 +1,12 @@
use crate::syscall::{sys_close, sys_dup, sys_exit, sys_open};
use crate::syscall::{O_RDONLY, O_WRONLY};
use crate::io::{O_RDONLY, O_WRONLY, STDIN, STDOUT};
use core::alloc::Layout;
use core::panic::PanicInfo;
// used for panic
macro_rules! print {
($($arg:tt)*) => ({
$crate::syscall::print_putc(format_args!($($arg)*));
$crate::io::print_putc(format_args!($($arg)*));
});
}
@ -33,11 +33,11 @@ fn initfd(fd2: usize, path: &str, open_flags: usize) -> i32 {
#[no_mangle]
pub extern "C" fn _start(_argc: isize, _argv: *const *const u8) -> ! {
let fd = initfd(0, "stdin:", O_RDONLY);
let fd = initfd(STDIN, "stdin:", O_RDONLY);
if fd < 0 {
panic!("open <stdin> failed: {}.", fd);
}
let fd = initfd(1, "stdout:", O_WRONLY);
let fd = initfd(STDOUT, "stdout:", O_WRONLY);
if fd < 0 {
panic!("open <stdout> failed: {}.", fd);
}

@ -6,5 +6,6 @@
#![feature(compiler_builtins_lib)]
#[macro_use]
pub mod io;
pub mod syscall;
pub mod lang_items;

@ -1,57 +1,10 @@
use core::fmt::{self, Write};
#[macro_export]
macro_rules! print {
($($arg:tt)*) => ({
$crate::syscall::print(format_args!($($arg)*));
});
}
#[macro_export]
macro_rules! println {
($fmt:expr) => (print!(concat!($fmt, "\n")));
($fmt:expr, $($arg:tt)*) => (print!(concat!($fmt, "\n"), $($arg)*));
}
pub fn print(args: fmt::Arguments) {
StdOut.write_fmt(args).unwrap();
}
pub fn print_putc(args: fmt::Arguments) {
SysPutc.write_fmt(args).unwrap();
}
struct StdOut;
struct SysPutc;
impl fmt::Write for StdOut {
fn write_str(&mut self, s: &str) -> fmt::Result {
if sys_write(1, s.as_ptr(), s.len()) >= 0 {
Ok(())
} else {
Err(fmt::Error::default())
}
}
}
impl fmt::Write for SysPutc {
fn write_str(&mut self, s: &str) -> fmt::Result {
for c in s.bytes() {
sys_putc(c as char);
}
Ok(())
}
}
#[inline(always)]
fn sys_call(id: usize, arg0: usize, arg1: usize, arg2: usize, arg3: usize, arg4: usize, arg5: usize) -> i32 {
#[cfg(target_arch = "riscv64")]
let ret: i32 = 0;
#[cfg(target_arch = "riscv32")]
fn sys_call(syscall_id: SyscallId, arg0: usize, arg1: usize, arg2: usize, arg3: usize, arg4: usize, arg5: usize) -> i32 {
let id = syscall_id as usize;
let ret: i32;
unsafe {
#[cfg(target_arch = "riscv32")]
#[cfg(any(target_arch = "riscv32", target_arch = "riscv64"))]
asm!("ecall"
: "={x10}" (ret)
: "{x10}" (id), "{x11}" (arg0), "{x12}" (arg1), "{x13}" (arg2), "{x14}" (arg3), "{x15}" (arg4), "{x16}" (arg5)
@ -74,12 +27,21 @@ fn sys_call(id: usize, arg0: usize, arg1: usize, arg2: usize, arg3: usize, arg4:
}
pub fn sys_exit(code: usize) -> ! {
sys_call(SYS_EXIT, code, 0, 0, 0, 0, 0);
sys_call(SyscallId::Exit, code, 0, 0, 0, 0, 0);
unreachable!()
}
pub fn sys_exec(name: *const u8, argc: usize, argv: *const *const u8) -> i32 {
sys_call(SyscallId::Exec, name as usize, argc, argv as usize, 0, 0, 0)
}
pub fn sys_write(fd: usize, base: *const u8, len: usize) -> i32 {
sys_call(SYS_WRITE, fd, base as usize, len, 0, 0, 0)
sys_call(SyscallId::Write, fd, base as usize, len, 0, 0, 0)
}
pub fn sys_read(fd: usize, base: *mut u8, len: usize) -> i32 {
sys_call(SyscallId::Read, fd, base as usize, len, 0, 0, 0)
}
pub fn sys_open(path: &str, flags: usize) -> i32 {
@ -87,95 +49,86 @@ pub fn sys_open(path: &str, flags: usize) -> i32 {
use core::mem::replace;
let end = unsafe { &mut *(path.as_ptr().offset(path.len() as isize) as *mut u8) };
let backup = replace(end, 0);
let ret = sys_call(SYS_OPEN, path.as_ptr() as usize, flags, 0, 0, 0, 0);
let ret = sys_call(SyscallId::Open, path.as_ptr() as usize, flags, 0, 0, 0, 0);
*end = backup;
ret
}
pub fn sys_close(fd: usize) -> i32 {
sys_call(SYS_CLOSE, fd, 0, 0, 0, 0, 0)
sys_call(SyscallId::Close, fd, 0, 0, 0, 0, 0)
}
pub fn sys_dup(fd1: usize, fd2: usize) -> i32 {
sys_call(SYS_DUP, fd1, fd2, 0, 0, 0, 0)
sys_call(SyscallId::Dup, fd1, fd2, 0, 0, 0, 0)
}
/// Fork the current process. Return the child's PID.
pub fn sys_fork() -> i32 {
sys_call(SYS_FORK, 0, 0, 0, 0, 0, 0)
sys_call(SyscallId::Fork, 0, 0, 0, 0, 0, 0)
}
/// Wait the process exit.
/// Return the PID. Store exit code to `code` if it's not null.
pub fn sys_wait(pid: usize, code: *mut i32) -> i32 {
sys_call(SYS_WAIT, pid, code as usize, 0, 0, 0, 0)
sys_call(SyscallId::Wait, pid, code as usize, 0, 0, 0, 0)
}
pub fn sys_yield() -> i32 {
sys_call(SYS_YIELD, 0, 0, 0, 0, 0, 0)
sys_call(SyscallId::Yield, 0, 0, 0, 0, 0, 0)
}
/// Kill the process
pub fn sys_kill(pid: usize) -> i32 {
sys_call(SYS_KILL, pid, 0, 0, 0, 0, 0)
sys_call(SyscallId::Kill, pid, 0, 0, 0, 0, 0)
}
/// Get the current process id
pub fn sys_getpid() -> i32 {
sys_call(SYS_GETPID, 0, 0, 0, 0, 0, 0)
sys_call(SyscallId::GetPid, 0, 0, 0, 0, 0, 0)
}
pub fn sys_sleep(time: usize) -> i32 {
sys_call(SYS_SLEEP, time, 0, 0, 0, 0, 0)
sys_call(SyscallId::Sleep, time, 0, 0, 0, 0, 0)
}
pub fn sys_get_time() -> i32 {
sys_call(SYS_GETTIME, 0, 0, 0, 0, 0, 0)
sys_call(SyscallId::GetTime, 0, 0, 0, 0, 0, 0)
}
pub fn sys_lab6_set_priority(priority: usize) -> i32 {
sys_call(SYS_LAB6_SET_PRIORITY, priority, 0, 0, 0, 0, 0)
}
pub fn sys_putc(c: char) -> i32 {
sys_call(SYS_PUTC, c as usize, 0, 0, 0, 0, 0)
}
const SYS_EXIT: usize = 1;
const SYS_FORK: usize = 2;
const SYS_WAIT: usize = 3;
const SYS_EXEC: usize = 4;
const SYS_CLONE: usize = 5;
const SYS_YIELD: usize = 10;
const SYS_SLEEP: usize = 11;
const SYS_KILL: usize = 12;
const SYS_GETTIME: usize = 17;
const SYS_GETPID: usize = 18;
const SYS_MMAP: usize = 20;
const SYS_MUNMAP: usize = 21;
const SYS_SHMEM: usize = 22;
const SYS_PUTC: usize = 30;
const SYS_PGDIR: usize = 31;
const SYS_OPEN: usize = 100;
const SYS_CLOSE: usize = 101;
const SYS_READ: usize = 102;
const SYS_WRITE: usize = 103;
const SYS_SEEK: usize = 104;
const SYS_FSTAT: usize = 110;
const SYS_FSYNC: usize = 111;
const SYS_GETCWD: usize = 121;
const SYS_GETDIRENTRY: usize = 128;
const SYS_DUP: usize = 130;
const SYS_LAB6_SET_PRIORITY: usize = 255;
/* VFS flags */
// TODO: use bitflags
// flags for open: choose one of these
pub const O_RDONLY: usize = 0; // open for reading only
pub const O_WRONLY: usize = 1; // open for writing only
pub const O_RDWR: usize = 2; // open for reading and writing
// then or in any of these:
pub const O_CREAT: usize = 0x00000004; // create file if it does not exist
pub const O_EXCL: usize = 0x00000008; // error if O_CREAT and the file exists
pub const O_TRUNC: usize = 0x00000010; // truncate file upon open
pub const O_APPEND: usize = 0x00000020; // append on each write
sys_call(SyscallId::Lab6SetPriority, priority, 0, 0, 0, 0, 0)
}
pub fn sys_putc(c: u8) -> i32 {
sys_call(SyscallId::Putc, c as usize, 0, 0, 0, 0, 0)
}
#[allow(dead_code)]
enum SyscallId{
Exit = 1,
Fork = 2,
Wait = 3,
Exec = 4,
Clone = 5,
Yield = 10,
Sleep = 11,
Kill = 12,
GetTime = 17,
GetPid = 18,
Mmap = 20,
Munmap = 21,
Shmem = 22,
Putc = 30,
Pgdir = 31,
Open = 100,
Close = 101,
Read = 102,
Write = 103,
Seek = 104,
Fstat = 110,
Fsync = 111,
GetCwd = 121,
GetDirEntry = 128,
Dup = 130,
Lab6SetPriority = 255,
}

Loading…
Cancel
Save