-
Notifications
You must be signed in to change notification settings - Fork 2
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
2 changed files
with
122 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,74 @@ | ||
//! The `powerctl` command implements power control features such as shutdown, reboot, halt, etc... | ||
mod power; | ||
|
||
use power::halt; | ||
use power::poweroff; | ||
use power::reboot; | ||
use power::suspend; | ||
use std::env; | ||
use std::env::ArgsOs; | ||
use std::process::exit; | ||
use utils::error; | ||
|
||
/// Prints command usage. | ||
/// | ||
/// `name` is the name of the binary. | ||
fn print_usage(name: &str) { | ||
println!("Usage:"); | ||
println!(" {name} [-f] [-n]"); | ||
println!(); | ||
println!("Controls the system's power."); | ||
println!(); | ||
println!("Options:"); | ||
println!(" -f\tforce operation without stopping services"); | ||
println!(" -n\tdon't synchronize storage"); | ||
} | ||
|
||
/// Input arguments. | ||
struct Args { | ||
/// If true, the command forces the operation and doesn't stop services. | ||
force: bool, | ||
/// If true, the command doesn't sync storage. | ||
no_sync: bool, | ||
} | ||
|
||
/// Parses arguments from the given array. | ||
fn parse_args(args: ArgsOs) -> Args { | ||
let mut res = Args { | ||
force: false, | ||
no_sync: false, | ||
}; | ||
for arg in args { | ||
match arg.to_str() { | ||
Some("-f" | "--force") => res.force = true, | ||
Some("-n" | "--no-sync") => res.no_sync = true, | ||
_ => error( | ||
"powerctl", | ||
format_args!("invalid argument `{}`", arg.display()), | ||
), | ||
} | ||
} | ||
res | ||
} | ||
|
||
pub fn main(bin: &str, args: ArgsOs) { | ||
// Parse arguments | ||
let args = parse_args(args); | ||
if !args.force { | ||
// TODO Stop services | ||
} | ||
if !args.no_sync { | ||
// TODO Sync storage | ||
} | ||
match bin { | ||
"shutdown" | "poweroff" => poweroff(), | ||
"reboot" => reboot(), | ||
"halt" => halt(), | ||
"suspend" => suspend(), | ||
_ => { | ||
print_usage(bin); | ||
exit(1); | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,48 @@ | ||
//! This module handles power management system calls. | ||
use std::os::raw::c_long; | ||
|
||
/// The ID of the `reboot` system call. | ||
const REBOOT_ID: c_long = 0x58; | ||
|
||
/// First magic number. | ||
const MAGIC: u32 = 0xde145e83; | ||
/// Second magic number. | ||
const MAGIC2: u32 = 0x40367d6e; | ||
|
||
/// Command to power off the system. | ||
const CMD_POWEROFF: u32 = 0; | ||
/// Command to reboot the system. | ||
const CMD_REBOOT: u32 = 1; | ||
/// Command to halt the system. | ||
const CMD_HALT: u32 = 2; | ||
/// Command to suspend the system. | ||
const CMD_SUSPEND: u32 = 3; | ||
|
||
/// Power off the system. | ||
pub fn poweroff() { | ||
unsafe { | ||
libc::syscall(REBOOT_ID, MAGIC, MAGIC2, CMD_POWEROFF); | ||
} | ||
} | ||
|
||
/// Reboots the system. | ||
pub fn reboot() { | ||
unsafe { | ||
libc::syscall(REBOOT_ID, MAGIC, MAGIC2, CMD_REBOOT); | ||
} | ||
} | ||
|
||
/// Halts the system. | ||
pub fn halt() { | ||
unsafe { | ||
libc::syscall(REBOOT_ID, MAGIC, MAGIC2, CMD_HALT); | ||
} | ||
} | ||
|
||
/// Suspends the system. | ||
pub fn suspend() { | ||
unsafe { | ||
libc::syscall(REBOOT_ID, MAGIC, MAGIC2, CMD_SUSPEND); | ||
} | ||
} |