    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57

    //! The main module and entrypoint
    //!
    //! Various facilities of the kernels are implemented as submodules. The most
    //! important ones are:
    //!
    //! - [`trap`]: Handles all cases of switching from userspace to the kernel
    //! - [`syscall`]: System call handling and implementation
    //!
    //! The operating system also starts in this module. Kernel code starts
    //! executing from `entry.asm`, after which [`rust_main()`] is called to
    //! initialize various pieces of functionality. (See its source code for
    //! details.)
    //!
    //! We then call [`batch::run_next_app()`] and for the first time go to
    //! userspace.

    #![deny(missing_docs)]
    #![deny(warnings)]
    #![no_std]
    #![no_main]
    #![feature(panic_info_message)]

    use core::arch::global_asm;

    #[macro_use]
    mod console;
    pub mod batch;
    mod lang_items;
    mod sbi;
    mod sync;
    pub mod syscall;
    pub mod trap;

    global_asm!(include_str!("entry.asm"));
    global_asm!(include_str!("link_app.S"));

    /// clear BSS segment
    fn clear_bss() {
        extern "C" {
            fn sbss();
            fn ebss();
        }
        unsafe {
            core::slice::from_raw_parts_mut(sbss as usize as *mut u8, ebss as usize - sbss as usize)
                .fill(0);
        }
    }

    /// the rust entry-point of os
    #[no_mangle]
    pub fn rust_main() -> ! {
        clear_bss();
        println!("[kernel] Hello, world!");
        trap::init();
        batch::init();
        batch::run_next_app();
    }