mirror of
https://github.com/uutils/coreutils.git
synced 2026-05-06 07:26:38 -04:00
fix(stat, mknod): replace custom (flawed in stat) logic with libc's.
Now uucore::fs reexports libc's major(), minor() and makedev() directives.
This commit is contained in:
@@ -86,6 +86,7 @@ listxattr
|
||||
llistxattr
|
||||
lossily
|
||||
lstat
|
||||
makedev
|
||||
mebi
|
||||
mebibytes
|
||||
mergeable
|
||||
|
||||
@@ -21,7 +21,7 @@ path = "src/mknod.rs"
|
||||
[dependencies]
|
||||
clap = { workspace = true }
|
||||
libc = { workspace = true }
|
||||
uucore = { workspace = true, features = ["mode"] }
|
||||
uucore = { workspace = true, features = ["mode", "fs"] }
|
||||
fluent = { workspace = true }
|
||||
|
||||
[features]
|
||||
|
||||
@@ -13,6 +13,7 @@ use std::ffi::CString;
|
||||
use uucore::display::Quotable;
|
||||
use uucore::error::{UResult, USimpleError, UUsageError, set_exit_code};
|
||||
use uucore::format_usage;
|
||||
use uucore::fs::makedev;
|
||||
use uucore::translate;
|
||||
|
||||
const MODE_RW_UGO: mode_t = S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH | S_IWOTH;
|
||||
@@ -26,12 +27,6 @@ mod options {
|
||||
pub const CONTEXT: &str = "context";
|
||||
}
|
||||
|
||||
#[inline(always)]
|
||||
fn makedev(maj: u64, min: u64) -> dev_t {
|
||||
// pick up from <sys/sysmacros.h>
|
||||
((min & 0xff) | ((maj & 0xfff) << 8) | ((min & !0xff) << 12) | ((maj & !0xfff) << 32)) as dev_t
|
||||
}
|
||||
|
||||
#[derive(Clone, PartialEq)]
|
||||
enum FileType {
|
||||
Block,
|
||||
@@ -145,7 +140,7 @@ pub fn uumain(args: impl uucore::Args) -> UResult<()> {
|
||||
translate!("mknod-error-fifo-no-major-minor"),
|
||||
));
|
||||
}
|
||||
(_, Some(&major), Some(&minor)) => makedev(major, minor),
|
||||
(_, Some(&major), Some(&minor)) => makedev(major as _, minor as _),
|
||||
_ => {
|
||||
return Err(UUsageError::new(
|
||||
1,
|
||||
|
||||
+7
-17
@@ -9,7 +9,7 @@ use uucore::translate;
|
||||
|
||||
use clap::builder::ValueParser;
|
||||
use uucore::display::Quotable;
|
||||
use uucore::fs::display_permissions;
|
||||
use uucore::fs::{display_permissions, major, minor};
|
||||
use uucore::fsext::{
|
||||
FsMeta, MetadataTimeField, StatFs, metadata_get_time, pretty_filetype, pretty_fstype,
|
||||
read_fs_list, statfs,
|
||||
@@ -301,16 +301,6 @@ fn group_num(s: &str) -> Cow<'_, str> {
|
||||
res.into()
|
||||
}
|
||||
|
||||
/// Keeps major part of an integer
|
||||
fn major(n: u64) -> u64 {
|
||||
(n >> 8) & 0xFF
|
||||
}
|
||||
|
||||
// Keeps minor part of an integer
|
||||
fn minor(n: u64) -> u64 {
|
||||
n & 0xFF
|
||||
}
|
||||
|
||||
struct Stater {
|
||||
follow: bool,
|
||||
show_fs: bool,
|
||||
@@ -1075,8 +1065,8 @@ impl Stater {
|
||||
}
|
||||
}
|
||||
// device number in decimal
|
||||
'd' if flag.major => OutputType::Unsigned(major(meta.dev())),
|
||||
'd' if flag.minor => OutputType::Unsigned(minor(meta.dev())),
|
||||
'd' if flag.major => OutputType::Unsigned(major(meta.dev() as _) as u64),
|
||||
'd' if flag.minor => OutputType::Unsigned(minor(meta.dev() as _) as u64),
|
||||
'd' => OutputType::Unsigned(meta.dev()),
|
||||
// device number in hex
|
||||
'D' => OutputType::UnsignedHex(meta.dev()),
|
||||
@@ -1115,10 +1105,10 @@ impl Stater {
|
||||
's' => OutputType::Integer(meta.len() as i64),
|
||||
// major device type in hex, for character/block device special
|
||||
// files
|
||||
't' => OutputType::UnsignedHex(major(meta.rdev())),
|
||||
't' => OutputType::UnsignedHex(major(meta.rdev() as _) as u64),
|
||||
// minor device type in hex, for character/block device special
|
||||
// files
|
||||
'T' => OutputType::UnsignedHex(minor(meta.rdev())),
|
||||
'T' => OutputType::UnsignedHex(minor(meta.rdev() as _) as u64),
|
||||
// user ID of owner
|
||||
'u' => OutputType::Unsigned(meta.uid() as u64),
|
||||
// user name of owner
|
||||
@@ -1162,8 +1152,8 @@ impl Stater {
|
||||
OutputType::Float(sec as f64 + nsec as f64 / 1_000_000_000.0)
|
||||
}
|
||||
'R' => OutputType::UnsignedHex(meta.rdev()),
|
||||
'r' if flag.major => OutputType::Unsigned(major(meta.rdev())),
|
||||
'r' if flag.minor => OutputType::Unsigned(minor(meta.rdev())),
|
||||
'r' if flag.major => OutputType::Unsigned(major(meta.rdev() as _) as u64),
|
||||
'r' if flag.minor => OutputType::Unsigned(minor(meta.rdev() as _) as u64),
|
||||
'r' => OutputType::Unsigned(meta.rdev()),
|
||||
_ => OutputType::Unknown,
|
||||
};
|
||||
|
||||
@@ -13,6 +13,8 @@ use libc::{
|
||||
S_IRUSR, S_ISGID, S_ISUID, S_ISVTX, S_IWGRP, S_IWOTH, S_IWUSR, S_IXGRP, S_IXOTH, S_IXUSR,
|
||||
mkfifo, mode_t,
|
||||
};
|
||||
#[cfg(all(unix, not(target_os = "redox")))]
|
||||
pub use libc::{major, makedev, minor};
|
||||
use std::collections::HashSet;
|
||||
use std::collections::VecDeque;
|
||||
use std::env;
|
||||
@@ -839,6 +841,24 @@ pub fn make_fifo(path: &Path) -> std::io::Result<()> {
|
||||
}
|
||||
}
|
||||
|
||||
// Redox's libc appears not to include the following utilities
|
||||
|
||||
#[cfg(target_os = "redox")]
|
||||
pub fn major(dev: libc::dev_t) -> libc::c_uint {
|
||||
(((dev >> 8) & 0xFFF) | ((dev >> 32) & 0xFFFFF000)) as _
|
||||
}
|
||||
|
||||
#[cfg(target_os = "redox")]
|
||||
pub fn minor(dev: libc::dev_t) -> libc::c_uint {
|
||||
((dev & 0xFF) | ((dev >> 12) & 0xFFFFF00)) as _
|
||||
}
|
||||
|
||||
#[cfg(target_os = "redox")]
|
||||
pub fn makedev(maj: libc::c_uint, min: libc::c_uint) -> libc::dev_t {
|
||||
let [maj, min] = [maj as libc::dev_t, min as libc::dev_t];
|
||||
(min & 0xff) | ((maj & 0xfff) << 8) | ((min & !0xff) << 12) | ((maj & !0xfff) << 32)
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
// Note this useful idiom: importing names from outer (for mod tests) scope.
|
||||
|
||||
Reference in New Issue
Block a user