commit c1065c7c2f48873361cc929c71eb418885d4d908 Author: Mitchell Date: Wed Apr 5 00:35:46 2023 -0500 init diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..3570cad --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +/target +/driver_samples diff --git a/Cargo.lock b/Cargo.lock new file mode 100644 index 0000000..79f2122 --- /dev/null +++ b/Cargo.lock @@ -0,0 +1,85 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + +[[package]] +name = "anyhow" +version = "1.0.70" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7de8ce5e0f9f8d88245311066a578d72b7af3e7088f32783804676302df237e4" + +[[package]] +name = "dataview" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "50eb3a329e19d78c3a3dfa4ec5a51ecb84fa3a20c06edad04be25356018218f9" +dependencies = [ + "derive_pod", +] + +[[package]] +name = "derive_pod" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c2ea6706d74fca54e15f1d40b5cf7fe7f764aaec61352a9fcec58fe27e042fc8" + +[[package]] +name = "driver-scanner" +version = "0.1.0" +dependencies = [ + "anyhow", + "pelite", +] + +[[package]] +name = "libc" +version = "0.2.141" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3304a64d199bb964be99741b7a14d26972741915b3649639149b2479bb46f4b5" + +[[package]] +name = "no-std-compat" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b93853da6d84c2e3c7d730d6473e8817692dd89be387eb01b94d7f108ecb5b8c" + +[[package]] +name = "pelite" +version = "0.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "88dccf4bd32294364aeb7bd55d749604450e9db54605887551f21baea7617685" +dependencies = [ + "dataview", + "libc", + "no-std-compat", + "pelite-macros", + "winapi", +] + +[[package]] +name = "pelite-macros" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7a7cf3f8ecebb0f4895f4892a8be0a0dc81b498f9d56735cb769dc31bf00815b" + +[[package]] +name = "winapi" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419" +dependencies = [ + "winapi-i686-pc-windows-gnu", + "winapi-x86_64-pc-windows-gnu", +] + +[[package]] +name = "winapi-i686-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" + +[[package]] +name = "winapi-x86_64-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" diff --git a/Cargo.toml b/Cargo.toml new file mode 100644 index 0000000..10a75a8 --- /dev/null +++ b/Cargo.toml @@ -0,0 +1,10 @@ +[package] +name = "driver-scanner" +version = "0.1.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] +pelite = "0.10.0" +anyhow = "1.0.40" diff --git a/src/main.rs b/src/main.rs new file mode 100644 index 0000000..39d5430 --- /dev/null +++ b/src/main.rs @@ -0,0 +1,70 @@ +use anyhow::{Context, Result}; +use pelite::{ + pe64::{imports::Import, Pe, PeFile}, + FileMap, +}; + +fn main() -> Result<()> { + let directory = std::env::args().nth(1).expect("No directory given."); + + let files = std::fs::read_dir(directory)?; + + for file in files { + let path = file?.path(); + let path = path.to_str().context("Bad filepath")?; + + println!("Parsing: {}", path); + + match parse_file_imports(path) { + Ok(imports) => { + if check_for_imports(&imports, &["MmMapIoSpace", "MmUnmapIoSpace"]) { + println!("{} contains MmMapIoSpace and MmUnmapIoSpace", path); + } + if check_for_imports(&imports, &["ZwMapViewOfSection", "ZwUnmapViewOfSection"]) { + println!( + "{} contains ZwMapViewOfSection and ZwUnmapViewOfSection", + path + ); + } + } + Err(e) => { + println!("Error: {}", e); + } + } + + println!(); + } + + Ok(()) +} + +fn parse_file_imports(path: &str) -> Result> { + if !path.ends_with(".sys") { + return Err(anyhow::anyhow!("Not a .sys file")); + } + + let file_map = FileMap::open(&path)?; + let pe = PeFile::from_bytes(file_map.as_ref())?; + + let vals = pe + .iat()? + .iter() + .filter_map(|(_a, import)| import.ok()) + .filter_map(|import| { + if let Import::ByName { name, .. } = import { + return name.to_str().ok().clone(); + } + None + }) + .map(String::from) + .collect(); + + Ok(vals) +} + +// TODO: check for actually import name and return e.g. MmMapIoSpaceEx +fn check_for_imports(imports: &[String], contains: &[&str]) -> bool { + contains + .iter() + .all(|cont| imports.iter().any(|imp| imp.starts_with(cont))) +}