diff --git a/Makefile b/Makefile index 2d7a3fbdd..580d1cc51 100644 --- a/Makefile +++ b/Makefile @@ -453,14 +453,16 @@ check: initramfs $(CARGO_OSDK) @# Check compilation of the Rust code @for dir in $(NON_OSDK_CRATES); do \ echo "Checking $$dir"; \ - (cd $$dir && cargo clippy -- -D warnings) || exit 1; \ + (cd $$dir && cargo clippy --no-deps -- -D warnings) || exit 1; \ done @for dir in $(OSDK_CRATES); do \ echo "Checking $$dir"; \ # Exclude linux-bzimage-setup since it only supports x86-64 currently and will panic \ # in other architectures. \ [ "$$dir" = "ostd/libs/linux-bzimage/setup" ] && [ "$(OSDK_TARGET_ARCH)" != "x86_64" ] && continue; \ - (cd $$dir && cargo osdk clippy -- -- -D warnings) || exit 1; \ + # Run clippy on each crate with and without the ktest configuration. \ + (cd $$dir && cargo osdk clippy -- --no-deps -- -D warnings) || exit 1; \ + (cd $$dir && cargo osdk clippy --ktest -- --no-deps -- -D warnings) || exit 1; \ done @ @# Check formatting issues of the C code and Nix files (regression tests) diff --git a/kernel/src/fs/configfs/mod.rs b/kernel/src/fs/configfs/mod.rs index 868982973..76704dc9b 100644 --- a/kernel/src/fs/configfs/mod.rs +++ b/kernel/src/fs/configfs/mod.rs @@ -28,6 +28,7 @@ pub(super) fn init() { /// this function returns an error. /// /// [`ConfigFs`]: fs::ConfigFs +#[cfg_attr(not(ktest), expect(dead_code))] pub fn register_subsystem(subsystem: Arc) -> Result<()> { ConfigRootNode::singleton().add_child(subsystem)?; diff --git a/kernel/src/fs/utils/inode.rs b/kernel/src/fs/utils/inode.rs index 97e64f39a..2431add2e 100644 --- a/kernel/src/fs/utils/inode.rs +++ b/kernel/src/fs/utils/inode.rs @@ -510,16 +510,19 @@ impl dyn Inode { self.read_at(offset, &mut writer, StatusFlags::empty()) } + #[cfg_attr(not(ktest), expect(dead_code))] pub fn write_bytes_at(&self, offset: usize, buf: &[u8]) -> Result { let mut reader = VmReader::from(buf).to_fallible(); self.write_at(offset, &mut reader, StatusFlags::empty()) } + #[cfg_attr(not(ktest), expect(dead_code))] pub fn read_bytes_direct_at(&self, offset: usize, buf: &mut [u8]) -> Result { let mut writer = VmWriter::from(buf).to_fallible(); self.read_at(offset, &mut writer, StatusFlags::O_DIRECT) } + #[cfg_attr(not(ktest), expect(dead_code))] pub fn write_bytes_direct_at(&self, offset: usize, buf: &[u8]) -> Result { let mut reader = VmReader::from(buf).to_fallible(); self.write_at(offset, &mut reader, StatusFlags::O_DIRECT) @@ -611,6 +614,7 @@ pub enum SymbolicLink { } impl SymbolicLink { + #[cfg_attr(not(ktest), expect(dead_code))] pub fn into_plain(self) -> Option { match self { SymbolicLink::Plain(s) => Some(s), diff --git a/kernel/src/fs/utils/mod.rs b/kernel/src/fs/utils/mod.rs index bd3beeb7c..d0f9e0987 100644 --- a/kernel/src/fs/utils/mod.rs +++ b/kernel/src/fs/utils/mod.rs @@ -20,6 +20,7 @@ pub use inode_mode::InodeMode; pub(crate) use inode_mode::{chmod, mkmod, perms_to_mask, who_and_perms_to_mask, who_to_mask}; pub use open_args::OpenArgs; pub use page_cache::{CachePage, PageCache, PageCacheBackend}; +#[cfg(ktest)] pub use random_test::{generate_random_operation, new_fs_in_memory}; pub use range_lock::{FileRange, OFFSET_MAX, RangeLockItem, RangeLockList, RangeLockType}; pub use status_flags::StatusFlags; @@ -44,6 +45,7 @@ mod inode_mode; pub mod ioctl_defs; mod open_args; mod page_cache; +#[cfg(ktest)] mod random_test; mod range_lock; mod status_flags; diff --git a/kernel/src/net/socket/netlink/table/mod.rs b/kernel/src/net/socket/netlink/table/mod.rs index 0e804cb43..5b2de99f8 100644 --- a/kernel/src/net/socket/netlink/table/mod.rs +++ b/kernel/src/net/socket/netlink/table/mod.rs @@ -57,6 +57,7 @@ pub trait SupportedNetlinkProtocol { socket_table.unicast(dst_port, message) } + #[cfg_attr(not(ktest), expect(dead_code))] fn multicast(dst_groups: GroupIdSet, message: Self::Message) -> Result<()> where Self::Message: MulticastMessage, diff --git a/kernel/src/thread/mod.rs b/kernel/src/thread/mod.rs index b304b70a3..c2bc4707b 100644 --- a/kernel/src/thread/mod.rs +++ b/kernel/src/thread/mod.rs @@ -147,6 +147,7 @@ impl Thread { /// /// This method will return after the thread exits. #[track_caller] + #[cfg_attr(not(ktest), expect(dead_code))] pub fn join(&self) { while !self.is_exited() { Self::yield_now(); diff --git a/kernel/src/vm/vmar/interval_set.rs b/kernel/src/vm/vmar/interval_set.rs index db7a77d87..d32bf460e 100644 --- a/kernel/src/vm/vmar/interval_set.rs +++ b/kernel/src/vm/vmar/interval_set.rs @@ -198,6 +198,7 @@ where } /// A draining iterator that iterates over intervals in an interval set. +#[cfg_attr(not(ktest), expect(dead_code))] #[derive(Debug)] pub struct IntervalDrain<'a, K, V> where diff --git a/osdk/deps/test-kernel/src/path.rs b/osdk/deps/test-kernel/src/path.rs index 95e672133..45f63e814 100644 --- a/osdk/deps/test-kernel/src/path.rs +++ b/osdk/deps/test-kernel/src/path.rs @@ -42,6 +42,7 @@ impl KtestPath { self.path.push_back(PathElement::from(s)); } + #[cfg_attr(not(ktest), expect(dead_code))] pub fn pop_back(&mut self) -> Option { self.path.pop_back() } @@ -64,6 +65,7 @@ impl KtestPath { self.path.is_empty() } + #[cfg_attr(not(ktest), expect(dead_code))] pub fn starts_with(&self, other: &Self) -> bool { if self.path.len() < other.path.len() { return false; @@ -76,6 +78,7 @@ impl KtestPath { true } + #[cfg_attr(not(ktest), expect(dead_code))] pub fn ends_with(&self, other: &Self) -> bool { if self.path.len() < other.path.len() { return false; @@ -199,6 +202,7 @@ impl SuffixTrie { } /// Find if there is a perfect match in this suffix trie. + #[cfg_attr(not(ktest), expect(dead_code))] pub fn matches(&self, path: I) -> bool where I: DoubleEndedIterator, diff --git a/osdk/src/cli.rs b/osdk/src/cli.rs index fe47fc99b..50e70b931 100644 --- a/osdk/src/cli.rs +++ b/osdk/src/cli.rs @@ -61,10 +61,10 @@ pub fn main() { execute_test_command(&load_config(&test_args.common_args), test_args); } OsdkSubcommand::Check(args) => { - execute_forwarded_command_on_each_crate("check", &args.args, true) + execute_forwarded_command_on_each_crate("check", &args.args, args.ktest) } OsdkSubcommand::Clippy(args) => { - execute_forwarded_command_on_each_crate("clippy", &args.args, true) + execute_forwarded_command_on_each_crate("clippy", &args.args, args.ktest) } OsdkSubcommand::Doc(args) => execute_forwarded_command("doc", &args.args, false), } @@ -99,13 +99,25 @@ pub enum OsdkSubcommand { #[command(about = "Execute kernel mode unit test by starting a VMM")] Test(TestArgs), #[command(about = "Check a local package and all of its dependencies for errors")] - Check(ForwardedArguments), + Check(KtestWithForwardedArguments), #[command(about = "Checks a package to catch common mistakes and improve your Rust code")] - Clippy(ForwardedArguments), + Clippy(KtestWithForwardedArguments), #[command(about = "Build a package's documentation")] Doc(ForwardedArguments), } +#[derive(Debug, Parser)] +pub struct KtestWithForwardedArguments { + #[arg(long, help = "Check all targets that have `ktest = true` set")] + pub ktest: bool, + #[arg( + help = "The full set of Cargo arguments", + trailing_var_arg = true, + allow_hyphen_values = true + )] + pub args: Vec, +} + #[derive(Debug, Parser)] pub struct ForwardedArguments { #[arg( diff --git a/ostd/src/mm/page_table/boot_pt.rs b/ostd/src/mm/page_table/boot_pt.rs index 3dbd91223..3cb5eedf5 100644 --- a/ostd/src/mm/page_table/boot_pt.rs +++ b/ostd/src/mm/page_table/boot_pt.rs @@ -202,6 +202,7 @@ impl BootPageTable { /// /// This function is unsafe because it can cause undefined behavior if the caller /// maps a page in the kernel address space. + #[cfg_attr(not(ktest), expect(dead_code))] pub unsafe fn protect_base_page( &mut self, virt_addr: Vaddr,