oursh/program/posix/builtin/
exit.rs

1use std::{
2    process,
3    ffi::CString,
4};
5use nix::{
6    unistd::Pid,
7    sys::wait::WaitStatus,
8};
9use crate::{
10    program::posix::builtin::Builtin,
11    program::{Result, Runtime},
12};
13
14/// Exit builtin, alternative to ctrl-d.
15pub struct Exit;
16
17impl Builtin for Exit {
18    #[allow(unused_variables)]
19    fn run(self, argv: Vec<CString>, runtime: &mut Runtime) -> Result<WaitStatus> {
20        #[cfg(feature = "history")]
21        if argv.len() == 1 || argv.len() == 2 {
22            runtime.history.save().unwrap();
23        }
24
25        match argv.len() {
26            0 => {
27                panic!("command name not passed in argv[0]");
28            },
29            1 => {
30                process::exit(0)
31            },
32            2 => {
33                if let Ok(n) = str::parse(argv[1].to_str().unwrap()) {
34                    process::exit(n)
35                } else {
36                    process::exit(2)
37                }
38            },
39            _ => {
40                eprintln!("too many arguments");
41                Ok(WaitStatus::Exited(Pid::this(), 1))
42            }
43        }
44    }
45}