Implement ctrlaltdel
(#31)
* Implement ctrlaltdel * Add tests for `ctrlaltdel` * Bless the unit tests on unsupported platforms
This commit is contained in:
9
Cargo.lock
generated
9
Cargo.lock
generated
@@ -641,12 +641,21 @@ dependencies = [
|
||||
"rlimit",
|
||||
"tempfile",
|
||||
"textwrap",
|
||||
"uu_ctrlaltdel",
|
||||
"uu_lscpu",
|
||||
"uu_mountpoint",
|
||||
"uucore",
|
||||
"xattr",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "uu_ctrlaltdel"
|
||||
version = "0.0.1"
|
||||
dependencies = [
|
||||
"clap",
|
||||
"uucore",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "uu_lscpu"
|
||||
version = "0.0.1"
|
||||
|
@@ -27,6 +27,7 @@ default = ["feat_common_core"]
|
||||
feat_common_core = [
|
||||
"mountpoint",
|
||||
"lscpu",
|
||||
"ctrlaltdel",
|
||||
]
|
||||
|
||||
[workspace.dependencies]
|
||||
@@ -56,6 +57,7 @@ textwrap = { workspace = true }
|
||||
#
|
||||
lscpu = { optional = true, version = "0.0.1", package = "uu_lscpu", path = "src/uu/lscpu" }
|
||||
mountpoint = { optional = true, version = "0.0.1", package = "uu_mountpoint", path = "src/uu/mountpoint" }
|
||||
ctrlaltdel = { optional = true, version = "0.0.1", package = "uu_ctrlaltdel", path = "src/uu/ctrlaltdel" }
|
||||
|
||||
[dev-dependencies]
|
||||
pretty_assertions = "1"
|
||||
|
15
src/uu/ctrlaltdel/Cargo.toml
Normal file
15
src/uu/ctrlaltdel/Cargo.toml
Normal file
@@ -0,0 +1,15 @@
|
||||
[package]
|
||||
name = "uu_ctrlaltdel"
|
||||
version = "0.0.1"
|
||||
edition = "2021"
|
||||
|
||||
[lib]
|
||||
path = "src/ctrlaltdel.rs"
|
||||
|
||||
[[bin]]
|
||||
name = "ctrlaltdel"
|
||||
path = "src/main.rs"
|
||||
|
||||
[dependencies]
|
||||
uucore = { workspace = true }
|
||||
clap = { workspace = true }
|
7
src/uu/ctrlaltdel/ctrlaltdel.md
Normal file
7
src/uu/ctrlaltdel/ctrlaltdel.md
Normal file
@@ -0,0 +1,7 @@
|
||||
# ctrlaltdel
|
||||
|
||||
```
|
||||
ctrlaltdel hard|soft
|
||||
```
|
||||
|
||||
set the function of the ctrl-alt-del combination
|
139
src/uu/ctrlaltdel/src/ctrlaltdel.rs
Normal file
139
src/uu/ctrlaltdel/src/ctrlaltdel.rs
Normal file
@@ -0,0 +1,139 @@
|
||||
// This file is part of the uutils util-linux package.
|
||||
//
|
||||
// For the full copyright and license information, please view the LICENSE
|
||||
// file that was distributed with this source code.
|
||||
|
||||
use clap::{crate_version, Arg, ArgAction, Command};
|
||||
use uucore::{error::UResult, format_usage, help_about, help_usage};
|
||||
|
||||
const ABOUT: &str = help_about!("ctrlaltdel.md");
|
||||
const USAGE: &str = help_usage!("ctrlaltdel.md");
|
||||
|
||||
#[cfg(target_os = "linux")]
|
||||
const CTRL_ALT_DEL_PATH: &str = "/proc/sys/kernel/ctrl-alt-del";
|
||||
|
||||
#[cfg(target_os = "linux")]
|
||||
#[uucore::main]
|
||||
pub fn uumain(args: impl uucore::Args) -> UResult<()> {
|
||||
let matches: clap::ArgMatches = uu_app().try_get_matches_from(args)?;
|
||||
let pattern = matches.get_one::<String>("pattern");
|
||||
match pattern {
|
||||
Some(x) if x == "hard" => {
|
||||
set_ctrlaltdel(CtrlAltDel::Hard)?;
|
||||
}
|
||||
Some(x) if x == "soft" => {
|
||||
set_ctrlaltdel(CtrlAltDel::Soft)?;
|
||||
}
|
||||
Some(x) => {
|
||||
Err(Error::UnknownArgument(x.clone()))?;
|
||||
}
|
||||
None => {
|
||||
println!("{}", get_ctrlaltdel()?);
|
||||
}
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[cfg(not(target_os = "linux"))]
|
||||
#[uucore::main]
|
||||
pub fn uumain(args: impl uucore::Args) -> UResult<()> {
|
||||
let _matches: clap::ArgMatches = uu_app().try_get_matches_from(args)?;
|
||||
|
||||
Err(uucore::error::USimpleError::new(
|
||||
1,
|
||||
"`ctrlaltdel` is unavailable on current platform.",
|
||||
))
|
||||
}
|
||||
|
||||
#[cfg(target_os = "linux")]
|
||||
fn get_ctrlaltdel() -> UResult<CtrlAltDel> {
|
||||
let value: i32 = std::fs::read_to_string(CTRL_ALT_DEL_PATH)?
|
||||
.trim()
|
||||
.parse()
|
||||
.map_err(|_| Error::UnknownData)?;
|
||||
|
||||
Ok(CtrlAltDel::from_sysctl(value))
|
||||
}
|
||||
|
||||
#[cfg(target_os = "linux")]
|
||||
fn set_ctrlaltdel(ctrlaltdel: CtrlAltDel) -> UResult<()> {
|
||||
std::fs::write(CTRL_ALT_DEL_PATH, format!("{}\n", ctrlaltdel.to_sysctl()))
|
||||
.map_err(|_| Error::NotRoot)?;
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[cfg(target_os = "linux")]
|
||||
#[derive(Clone, Copy)]
|
||||
enum CtrlAltDel {
|
||||
Soft,
|
||||
Hard,
|
||||
}
|
||||
#[cfg(target_os = "linux")]
|
||||
impl CtrlAltDel {
|
||||
/// # Panics
|
||||
/// Panics if value of the parameter `value` is neither `0` nor `1`.
|
||||
fn from_sysctl(value: i32) -> Self {
|
||||
match value {
|
||||
0 => Self::Soft,
|
||||
1 => Self::Hard,
|
||||
_ => unreachable!(),
|
||||
}
|
||||
}
|
||||
|
||||
fn to_sysctl(self) -> i32 {
|
||||
match self {
|
||||
Self::Soft => 0,
|
||||
Self::Hard => 1,
|
||||
}
|
||||
}
|
||||
}
|
||||
#[cfg(target_os = "linux")]
|
||||
impl std::fmt::Display for CtrlAltDel {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
match self {
|
||||
Self::Soft => write!(f, "soft"),
|
||||
Self::Hard => write!(f, "hard"),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(target_os = "linux")]
|
||||
#[derive(Debug)]
|
||||
enum Error {
|
||||
NotRoot,
|
||||
UnknownArgument(String),
|
||||
UnknownData,
|
||||
}
|
||||
#[cfg(target_os = "linux")]
|
||||
impl std::fmt::Display for Error {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
match self {
|
||||
Self::NotRoot => write!(f, "You must be root to set the Ctrl-Alt-Del behavior"),
|
||||
Self::UnknownArgument(x) => write!(f, "unknown argument: {x}"),
|
||||
Self::UnknownData => write!(f, "unknown data"),
|
||||
}
|
||||
}
|
||||
}
|
||||
#[cfg(target_os = "linux")]
|
||||
impl std::error::Error for Error {}
|
||||
#[cfg(target_os = "linux")]
|
||||
impl uucore::error::UError for Error {
|
||||
fn code(&self) -> i32 {
|
||||
1
|
||||
}
|
||||
|
||||
fn usage(&self) -> bool {
|
||||
false
|
||||
}
|
||||
}
|
||||
|
||||
pub fn uu_app() -> Command {
|
||||
Command::new(uucore::util_name())
|
||||
.version(crate_version!())
|
||||
.about(ABOUT)
|
||||
.override_usage(format_usage(USAGE))
|
||||
.infer_long_args(true)
|
||||
.arg(Arg::new("pattern").action(ArgAction::Set))
|
||||
}
|
1
src/uu/ctrlaltdel/src/main.rs
Normal file
1
src/uu/ctrlaltdel/src/main.rs
Normal file
@@ -0,0 +1 @@
|
||||
uucore::bin!(uu_ctrlaltdel);
|
14
tests/by-util/test_ctrlaltdel.rs
Normal file
14
tests/by-util/test_ctrlaltdel.rs
Normal file
@@ -0,0 +1,14 @@
|
||||
// This file is part of the uutils util-linux package.
|
||||
//
|
||||
// For the full copyright and license information, please view the LICENSE
|
||||
// file that was distributed with this source code.
|
||||
// spell-checker:ignore (words) symdir somefakedir
|
||||
|
||||
#[cfg(target_os = "linux")]
|
||||
use crate::common::util::TestScenario;
|
||||
|
||||
#[test]
|
||||
#[cfg(target_os = "linux")]
|
||||
fn test_invalid_arg() {
|
||||
new_ucmd!().arg("--definitely-invalid").fails().code_is(1);
|
||||
}
|
@@ -12,3 +12,7 @@ mod test_lscpu;
|
||||
#[cfg(feature = "mountpoint")]
|
||||
#[path = "by-util/test_mountpoint.rs"]
|
||||
mod test_mountpoint;
|
||||
|
||||
#[cfg(feature = "ctrlaltdel")]
|
||||
#[path = "by-util/test_ctrlaltdel.rs"]
|
||||
mod test_ctrlaltdel;
|
||||
|
Reference in New Issue
Block a user