Add df
applet; Finalize some bootstrap details;
This commit is contained in:
parent
888cc3272b
commit
5a7c2008b5
41
Cargo.lock
generated
41
Cargo.lock
generated
@ -78,9 +78,9 @@ version = "0.1.0"
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "blake2b_simd"
|
name = "blake2b_simd"
|
||||||
version = "1.0.0"
|
version = "1.0.1"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "72936ee4afc7f8f736d1c38383b56480b5497b4617b4a77bdbf1d2ababc76127"
|
checksum = "3c2f0dc9a68c6317d884f97cc36cf5a3d20ba14ce404227df55e1af708ab04bc"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"arrayref",
|
"arrayref",
|
||||||
"arrayvec",
|
"arrayvec",
|
||||||
@ -169,9 +169,9 @@ dependencies = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "clap"
|
name = "clap"
|
||||||
version = "4.1.4"
|
version = "4.1.6"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "f13b9c79b5d1dd500d20ef541215a6423c75829ef43117e1b4d17fd8af0b5d76"
|
checksum = "ec0b0588d44d4d63a87dbd75c136c166bbfd9a86a31cb89e09906521c7d3f5e3"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"bitflags",
|
"bitflags",
|
||||||
"clap_lex",
|
"clap_lex",
|
||||||
@ -182,11 +182,11 @@ dependencies = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "clap_complete"
|
name = "clap_complete"
|
||||||
version = "4.1.1"
|
version = "4.1.2"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "3d6540eedc41f8a5a76cf3d8d458057dcdf817be4158a55b5f861f7a5483de75"
|
checksum = "bd125be87bf4c255ebc50de0b7f4d2a6201e8ac3dc86e39c0ad081dc5e7236fe"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"clap 4.1.4",
|
"clap 4.1.6",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
@ -195,7 +195,7 @@ version = "0.1.10"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "c7fa41f5e6aa83bd151b70fd0ceaee703d68cd669522795dc812df9edad1252c"
|
checksum = "c7fa41f5e6aa83bd151b70fd0ceaee703d68cd669522795dc812df9edad1252c"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"clap 4.1.4",
|
"clap 4.1.6",
|
||||||
"clap_complete",
|
"clap_complete",
|
||||||
]
|
]
|
||||||
|
|
||||||
@ -210,19 +210,19 @@ dependencies = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "clap_mangen"
|
name = "clap_mangen"
|
||||||
version = "0.2.7"
|
version = "0.2.8"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "eb258c6232b4d728d13d6072656627924c16707aae6267cd5a1ea05abff9a25c"
|
checksum = "48283ce8d5cd9513633949a674a0442bcb507ab61ed6533863437052ddbb494b"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"clap 4.1.4",
|
"clap 4.1.6",
|
||||||
"roff",
|
"roff",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "constant_time_eq"
|
name = "constant_time_eq"
|
||||||
version = "0.1.5"
|
version = "0.2.4"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "245097e9a4535ee1e3e3931fcfcd55a796a44c643e8596ff6566d68f09b87bbc"
|
checksum = "f3ad85c1f65dc7b37604eb0e89748faf0b9653065f2a8ef69f96a687ec1e9279"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "cpufeatures"
|
name = "cpufeatures"
|
||||||
@ -333,9 +333,9 @@ dependencies = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "hermit-abi"
|
name = "hermit-abi"
|
||||||
version = "0.3.0"
|
version = "0.3.1"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "856b5cb0902c2b6d65d5fd97dfa30f9b70c7538e770b98eab5ed52d8db923e01"
|
checksum = "fed44880c466736ef9a5c5b5facefb5ed0785676d0c02d612db14e54f0d84286"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "humantime"
|
name = "humantime"
|
||||||
@ -359,7 +359,7 @@ version = "0.4.3"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "22e18b0a45d56fe973d6db23972bf5bc46f988a4a2385deac9cc29572f09daef"
|
checksum = "22e18b0a45d56fe973d6db23972bf5bc46f988a4a2385deac9cc29572f09daef"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"hermit-abi 0.3.0",
|
"hermit-abi 0.3.1",
|
||||||
"io-lifetimes",
|
"io-lifetimes",
|
||||||
"rustix",
|
"rustix",
|
||||||
"windows-sys",
|
"windows-sys",
|
||||||
@ -578,7 +578,7 @@ dependencies = [
|
|||||||
"atty",
|
"atty",
|
||||||
"bitflags-mini",
|
"bitflags-mini",
|
||||||
"blake2b_simd",
|
"blake2b_simd",
|
||||||
"clap 4.1.4",
|
"clap 4.1.6",
|
||||||
"clap_complete",
|
"clap_complete",
|
||||||
"clap_complete_nushell",
|
"clap_complete_nushell",
|
||||||
"clap_mangen",
|
"clap_mangen",
|
||||||
@ -593,6 +593,7 @@ dependencies = [
|
|||||||
"sc",
|
"sc",
|
||||||
"sha1",
|
"sha1",
|
||||||
"sha2",
|
"sha2",
|
||||||
|
"size-display",
|
||||||
"termcolor",
|
"termcolor",
|
||||||
"textwrap 0.16.0",
|
"textwrap 0.16.0",
|
||||||
"unistd",
|
"unistd",
|
||||||
@ -606,6 +607,12 @@ version = "1.1.0"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "43b2853a4d09f215c24cc5489c992ce46052d359b5109343cbafbf26bc62f8a3"
|
checksum = "43b2853a4d09f215c24cc5489c992ce46052d359b5109343cbafbf26bc62f8a3"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "size-display"
|
||||||
|
version = "0.1.4"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "9df415f09e1c4d4f58cd0cd08b2f5385bc07cf1878e7a7846abc2225fa00e1e1"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "smawk"
|
name = "smawk"
|
||||||
version = "0.3.1"
|
version = "0.3.1"
|
||||||
|
@ -37,6 +37,7 @@ md5 = { version = "0.10", package = "md-5" }
|
|||||||
sc = { workspace = true }
|
sc = { workspace = true }
|
||||||
sha1 = "0.10"
|
sha1 = "0.10"
|
||||||
sha2 = "0.10"
|
sha2 = "0.10"
|
||||||
|
size-display = "0.1"
|
||||||
termcolor = "1.1"
|
termcolor = "1.1"
|
||||||
textwrap = { version = "0.16", default-features = false, features = ["smawk"] }
|
textwrap = { version = "0.16", default-features = false, features = ["smawk"] }
|
||||||
walkdir = "2.3"
|
walkdir = "2.3"
|
||||||
|
@ -27,6 +27,7 @@ code between applets, making for an overall smaller binary.
|
|||||||
- chroot
|
- chroot
|
||||||
- clear
|
- clear
|
||||||
- cut
|
- cut
|
||||||
|
- df
|
||||||
- dirname
|
- dirname
|
||||||
- echo
|
- echo
|
||||||
- false
|
- false
|
||||||
|
@ -395,4 +395,3 @@ fn links(prefix: &str, usr: bool, cmd: &ArgMatches) -> Result<(), Box<dyn Error>
|
|||||||
})?;
|
})?;
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
150
corebox/commands/df/mod.rs
Normal file
150
corebox/commands/df/mod.rs
Normal file
@ -0,0 +1,150 @@
|
|||||||
|
use clap::{Arg, ArgAction, ArgMatches, Command};
|
||||||
|
use mount::MntEntries;
|
||||||
|
use shitbox::Cmd;
|
||||||
|
use size_display::Size;
|
||||||
|
use std::{error::Error, fmt, io, path::PathBuf};
|
||||||
|
|
||||||
|
#[derive(Debug, Default)]
|
||||||
|
pub struct Df;
|
||||||
|
|
||||||
|
impl Cmd for Df {
|
||||||
|
fn cli(&self) -> Command {
|
||||||
|
Command::new("df")
|
||||||
|
.about("report free disk space")
|
||||||
|
.author("Nathan Fisher")
|
||||||
|
.version(env!("CARGO_PKG_VERSION"))
|
||||||
|
.disable_help_flag(true)
|
||||||
|
.args([
|
||||||
|
Arg::new("kilobytes")
|
||||||
|
.help("Use 1024-byte units, instead of the default 512-byte units, when writing space figures.")
|
||||||
|
.short('k')
|
||||||
|
.long("kilobytes")
|
||||||
|
.action(ArgAction::SetTrue),
|
||||||
|
Arg::new("human")
|
||||||
|
.help("print sizes in powers of 1024 (e.g., 1023M)")
|
||||||
|
.short('h')
|
||||||
|
.long("human-readable")
|
||||||
|
.conflicts_with("kilobytes")
|
||||||
|
.action(ArgAction::SetTrue),
|
||||||
|
Arg::new("file")
|
||||||
|
.value_name("FILE")
|
||||||
|
.num_args(1..)
|
||||||
|
])
|
||||||
|
}
|
||||||
|
|
||||||
|
fn run(&self, matches: &ArgMatches) -> Result<(), Box<dyn Error>> {
|
||||||
|
let units = if matches.get_flag("kilobytes") {
|
||||||
|
Units::Kilo
|
||||||
|
} else if matches.get_flag("human") {
|
||||||
|
Units::Natural
|
||||||
|
} else {
|
||||||
|
Units::Posix
|
||||||
|
};
|
||||||
|
println!("Filesystem {units} Used Avail Capacity Mounted on");
|
||||||
|
if let Some(files) = matches.get_many::<String>("file") {
|
||||||
|
for f in files {
|
||||||
|
let entry = MntEntries::new("/proc/mounts")?
|
||||||
|
.filter(|e| e.dir.as_str() == f)
|
||||||
|
.next()
|
||||||
|
.ok_or(io::Error::new(io::ErrorKind::Other, "no such filesystem"))?;
|
||||||
|
print_stats(&entry.fsname, &entry.dir, units)?;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
let entries = MntEntries::new("/proc/mounts")?.filter(|x| {
|
||||||
|
x.fstype != "proc"
|
||||||
|
&& x.fstype != "sysfs"
|
||||||
|
&& x.fstype != "securityfs"
|
||||||
|
&& x.fstype != "cgroup2"
|
||||||
|
&& x.fstype != "pstore"
|
||||||
|
&& x.fstype != "bpf"
|
||||||
|
&& x.fstype != "autofs"
|
||||||
|
&& x.fstype != "hugetlbfs"
|
||||||
|
&& x.fstype != "tracefs"
|
||||||
|
&& x.fstype != "debugfs"
|
||||||
|
&& x.fstype != "configfs"
|
||||||
|
&& x.fstype != "devpts"
|
||||||
|
&& x.fstype != "efivarfs"
|
||||||
|
&& x.fstype != "ramfs"
|
||||||
|
&& x.fstype != "binfmt_misc"
|
||||||
|
&& x.fstype != "fuse.gvfsd-fuse"
|
||||||
|
&& x.fstype != "fuse.portal"
|
||||||
|
&& x.fstype != "mqueue"
|
||||||
|
&& x.fstype != "fusectl"
|
||||||
|
});
|
||||||
|
for e in entries {
|
||||||
|
print_stats(&e.fsname, &e.dir, units)?;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
|
fn path(&self) -> Option<shitbox::Path> {
|
||||||
|
Some(shitbox::Path::UsrBin)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Clone, Copy, PartialEq)]
|
||||||
|
enum Units {
|
||||||
|
Posix,
|
||||||
|
Kilo,
|
||||||
|
Natural,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl fmt::Display for Units {
|
||||||
|
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||||
|
match self {
|
||||||
|
Self::Posix => write!(f, "512-blocks"),
|
||||||
|
Self::Kilo => write!(f, " 1K-blocks"),
|
||||||
|
Self::Natural => write!(f, " Size"),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn print_stats(fs: &str, mntpt: &str, units: Units) -> Result<(), Box<dyn Error>> {
|
||||||
|
let p = PathBuf::from(mntpt);
|
||||||
|
if p.exists() {
|
||||||
|
let st = shitbox::stat::statfs(mntpt)?;
|
||||||
|
let bs = match units {
|
||||||
|
Units::Posix => st.f_frsize / 512,
|
||||||
|
Units::Kilo => st.f_frsize / 1024,
|
||||||
|
Units::Natural => st.f_frsize,
|
||||||
|
};
|
||||||
|
let total = st.f_blocks * bs as u64;
|
||||||
|
let avail = st.f_bfree * bs as u64;
|
||||||
|
let used = total - avail;
|
||||||
|
let mut capacity = if total > 0 { (used * 100) / total } else { 0 };
|
||||||
|
if used * 100 != capacity * (used + avail) {
|
||||||
|
capacity += 1;
|
||||||
|
}
|
||||||
|
if units == Units::Natural {
|
||||||
|
print_human(fs, mntpt, total, avail, used, capacity);
|
||||||
|
return Ok(());
|
||||||
|
}
|
||||||
|
println!("{fs:<12} {total:>9} {used:>9} {avail:>9} {capacity:>7}% {mntpt}");
|
||||||
|
Ok(())
|
||||||
|
} else {
|
||||||
|
Err(io::Error::new(io::ErrorKind::Other, "fs does not exist").into())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn print_human(fs: &str, mntpt: &str, total: u64, avail: u64, used: u64, capacity: u64) {
|
||||||
|
// Unfortunately these strings must be printed separately due to the way the
|
||||||
|
// library formats size display, as 0 will be a shorter string due to having
|
||||||
|
// no suffix, throwing off column alignment
|
||||||
|
print!("{fs:<12}");
|
||||||
|
if total > 0 {
|
||||||
|
print!("{:>9.1}", Size(total));
|
||||||
|
} else {
|
||||||
|
print!("{total:>10}");
|
||||||
|
}
|
||||||
|
if used > 0 {
|
||||||
|
print!("{:>9.1}", Size(used));
|
||||||
|
} else {
|
||||||
|
print!("{used:>10}");
|
||||||
|
}
|
||||||
|
if avail > 0 {
|
||||||
|
println!("{:9.1} {capacity:>7}% {mntpt}", Size(avail));
|
||||||
|
} else {
|
||||||
|
println!("{avail:>10} {capacity:>7}% {mntpt}");
|
||||||
|
}
|
||||||
|
}
|
@ -14,6 +14,7 @@ mod cp;
|
|||||||
mod cut;
|
mod cut;
|
||||||
mod date;
|
mod date;
|
||||||
mod dd;
|
mod dd;
|
||||||
|
mod df;
|
||||||
mod dirname;
|
mod dirname;
|
||||||
mod echo;
|
mod echo;
|
||||||
mod expand;
|
mod expand;
|
||||||
@ -66,6 +67,7 @@ pub fn get(name: &str) -> Option<Box<dyn Cmd>> {
|
|||||||
"chroot" => Some(Box::new(chroot::Chroot::default())),
|
"chroot" => Some(Box::new(chroot::Chroot::default())),
|
||||||
"corebox" => Some(Box::new(corebox::Corebox::default())),
|
"corebox" => Some(Box::new(corebox::Corebox::default())),
|
||||||
"cut" => Some(Box::new(cut::Cut::default())),
|
"cut" => Some(Box::new(cut::Cut::default())),
|
||||||
|
"df" => Some(Box::new(df::Df::default())),
|
||||||
"dirname" => Some(Box::new(dirname::Dirname::default())),
|
"dirname" => Some(Box::new(dirname::Dirname::default())),
|
||||||
"echo" => Some(Box::new(echo::Echo::default())),
|
"echo" => Some(Box::new(echo::Echo::default())),
|
||||||
"factor" => Some(Box::new(factor::Factor::default())),
|
"factor" => Some(Box::new(factor::Factor::default())),
|
||||||
@ -102,7 +104,7 @@ pub fn get(name: &str) -> Option<Box<dyn Cmd>> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub static COMMANDS: [&str; 42] = [
|
pub static COMMANDS: [&str; 43] = [
|
||||||
"base32",
|
"base32",
|
||||||
"base64",
|
"base64",
|
||||||
"basename",
|
"basename",
|
||||||
@ -113,6 +115,7 @@ pub static COMMANDS: [&str; 42] = [
|
|||||||
"chroot",
|
"chroot",
|
||||||
"corebox",
|
"corebox",
|
||||||
"cut",
|
"cut",
|
||||||
|
"df",
|
||||||
"dirname",
|
"dirname",
|
||||||
"echo",
|
"echo",
|
||||||
"false",
|
"false",
|
||||||
|
@ -395,4 +395,3 @@ fn links(prefix: &str, usr: bool, cmd: &ArgMatches) -> Result<(), Box<dyn Error>
|
|||||||
})?;
|
})?;
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
use errno::Errno;
|
use errno::Errno;
|
||||||
use sc::*;
|
use sc::*;
|
||||||
use std::{ffi::CString, error::Error};
|
use std::{error::Error, ffi::CString};
|
||||||
|
|
||||||
mod mntent;
|
mod mntent;
|
||||||
mod mntentries;
|
mod mntentries;
|
||||||
|
@ -6,11 +6,12 @@ use blkid::{
|
|||||||
tag::{PartitionTag, SuperblockTag, TagType},
|
tag::{PartitionTag, SuperblockTag, TagType},
|
||||||
};
|
};
|
||||||
use std::{
|
use std::{
|
||||||
|
error::Error,
|
||||||
fmt::{self, Write},
|
fmt::{self, Write},
|
||||||
fs::File,
|
fs::File,
|
||||||
io::{self, BufRead, BufReader},
|
io::{self, BufRead, BufReader},
|
||||||
path::PathBuf,
|
path::PathBuf,
|
||||||
str::FromStr, error::Error,
|
str::FromStr,
|
||||||
};
|
};
|
||||||
|
|
||||||
/// The information for a mount broken out into a struct
|
/// The information for a mount broken out into a struct
|
||||||
|
@ -1,6 +1,12 @@
|
|||||||
use errno::Errno;
|
use errno::Errno;
|
||||||
use sc::*;
|
use sc::*;
|
||||||
use std::{ffi::CString, error::Error};
|
use std::{
|
||||||
|
error::Error,
|
||||||
|
ffi::{c_long, CString},
|
||||||
|
fs::File,
|
||||||
|
mem,
|
||||||
|
os::fd::AsRawFd,
|
||||||
|
};
|
||||||
|
|
||||||
#[inline(always)]
|
#[inline(always)]
|
||||||
pub fn mknod(path: &str, mode: u32, dev: u64) -> Result<(), Box<dyn Error>> {
|
pub fn mknod(path: &str, mode: u32, dev: u64) -> Result<(), Box<dyn Error>> {
|
||||||
@ -37,3 +43,17 @@ pub fn mkfifo(path: &str, mode: u32) -> Result<(), Box<dyn Error>> {
|
|||||||
Err(Errno::from(ret).into())
|
Err(Errno::from(ret).into())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline(always)]
|
||||||
|
pub fn statfs(dir: &str) -> Result<libc::statvfs, Box<dyn Error>> {
|
||||||
|
let mut buf = mem::MaybeUninit::<libc::statvfs>::uninit();
|
||||||
|
let fd = File::open(dir)?;
|
||||||
|
let ret = unsafe { libc::fstatvfs(fd.as_raw_fd(), buf.as_mut_ptr()) };
|
||||||
|
if ret == 0 {
|
||||||
|
let buf = unsafe { buf.assume_init() };
|
||||||
|
Ok(buf)
|
||||||
|
} else {
|
||||||
|
let e = unsafe { *libc::__errno_location() };
|
||||||
|
Err(Errno::from(e as c_long).into())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@ -395,4 +395,3 @@ fn links(prefix: &str, usr: bool, cmd: &ArgMatches) -> Result<(), Box<dyn Error>
|
|||||||
})?;
|
})?;
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user