diff --git a/fuzz/Cargo.lock b/fuzz/Cargo.lock index 1aa0fa138..5948ec3fd 100644 --- a/fuzz/Cargo.lock +++ b/fuzz/Cargo.lock @@ -102,6 +102,7 @@ dependencies = [ "thiserror", "versionize", "versionize_derive", + "vhdx", "virtio-bindings", "vm-memory 0.6.0", "vm-virtio", @@ -155,7 +156,7 @@ dependencies = [ "libc", "log", "option_parser", - "seccomp", + "seccompiler", "serde_json", "signal-hook", "thiserror", @@ -173,13 +174,23 @@ dependencies = [ "libc", "libfuzzer-sys", "qcow", - "seccomp", + "seccompiler", + "vhdx", "virtio-devices", "vm-memory 0.6.0", "vm-virtio", "vmm-sys-util", ] +[[package]] +name = "crc32c" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "210cdf933e6a81212bfabf90cd8762f471b5922e5f6b709547673ad8e04b9448" +dependencies = [ + "rustc_version", +] + [[package]] name = "crc64" version = "1.0.0" @@ -232,6 +243,17 @@ version = "0.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b643857cf70949306b81d7e92cb9d47add673868edac9863c4a49c42feaf3f1e" +[[package]] +name = "getrandom" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7fcd999463524c52659517fe2cea98493cfe485d10565e7b0fb07dbba7ad2753" +dependencies = [ + "cfg-if", + "libc", + "wasi", +] + [[package]] name = "hermit-abi" version = "0.1.19" @@ -463,6 +485,15 @@ dependencies = [ "syn", ] +[[package]] +name = "rustc_version" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "138e3e0acb6c9fb258b19b67cb8abd63c00679d2851805ea151465464fe9030a" +dependencies = [ + "semver", +] + [[package]] name = "ryu" version = "1.0.5" @@ -470,13 +501,28 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "71d301d4193d031abdd79ff7e3dd721168a9572ef3fe51a1517aba235bd8f86e" [[package]] -name = "seccomp" +name = "seccompiler" version = "0.1.0" -source = "git+https://github.com/firecracker-microvm/firecracker?tag=v0.24.5#cd36c699f3cb3d531289aadee26c45c1306edcfc" +source = "git+https://github.com/rust-vmm/seccompiler#da5788d52f1ae8886d8ed4624199b7e9fa64ac04" dependencies = [ "libc", ] +[[package]] +name = "semver" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1d7eb9ef2c18661902cc47e535f9bc51b78acd254da71d375c2f6720d9a40403" +dependencies = [ + "semver-parser", +] + +[[package]] +name = "semver-parser" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "388a1df253eca08550bef6c72392cfe7c30914bf41df5269b68cbd6ff8f570a3" + [[package]] name = "serde" version = "1.0.127" @@ -604,6 +650,9 @@ name = "uuid" version = "0.8.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bc5cf98d8186244414c848017f0e2676b3fcb46807f6668a97dfe67359a3c4b7" +dependencies = [ + "getrandom", +] [[package]] name = "vec_map" @@ -677,6 +726,20 @@ dependencies = [ "vmm-sys-util", ] +[[package]] +name = "vhdx" +version = "0.1.0" +dependencies = [ + "byteorder", + "crc32c", + "libc", + "log", + "remain", + "thiserror", + "uuid", + "vmm-sys-util", +] + [[package]] name = "vhost" version = "0.1.0" @@ -712,7 +775,7 @@ dependencies = [ "net_util", "pci", "rate_limiter", - "seccomp", + "seccompiler", "serde", "serde_derive", "serde_json", @@ -824,7 +887,7 @@ dependencies = [ "option_parser", "pci", "qcow", - "seccomp", + "seccompiler", "serde", "serde_derive", "serde_json", @@ -834,6 +897,7 @@ dependencies = [ "versionize", "versionize_derive", "vfio-ioctls", + "vhdx", "virtio-devices", "vm-allocator", "vm-device", @@ -855,6 +919,12 @@ dependencies = [ "serde_derive", ] +[[package]] +name = "wasi" +version = "0.10.2+wasi-snapshot-preview1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fd6fbd9a79829dd1ad0cc20627bf1ed606756a7f77edff7b66b7064f9cb327c6" + [[package]] name = "winapi" version = "0.3.9" diff --git a/fuzz/Cargo.toml b/fuzz/Cargo.toml index ff57021dd..c193e97d1 100644 --- a/fuzz/Cargo.toml +++ b/fuzz/Cargo.toml @@ -14,6 +14,7 @@ libc = "0.2.99" libfuzzer-sys = "0.4.2" qcow = { path = "../qcow" } seccompiler = { git = "https://github.com/rust-vmm/seccompiler"} +vhdx = { path = "../vhdx" } virtio-devices = { path = "../virtio-devices" } vmm-sys-util = "0.8.0" vm-virtio = { path = "../vm-virtio" } @@ -42,3 +43,9 @@ name = "block" path = "fuzz_targets/block.rs" test = false doc = false + +[[bin]] +name = "vhdx" +path = "fuzz_targets/vhdx.rs" +test = false +doc = false diff --git a/fuzz/fuzz_targets/vhdx.rs b/fuzz/fuzz_targets/vhdx.rs new file mode 100644 index 000000000..c3d372e83 --- /dev/null +++ b/fuzz/fuzz_targets/vhdx.rs @@ -0,0 +1,53 @@ +// Copyright © 2021 Intel Corporation +// +// SPDX-License-Identifier: Apache-2.0 + +#![no_main] +use libfuzzer_sys::fuzz_target; +use std::ffi; +use std::fs::File; +use std::io::{self, Read, Seek, SeekFrom, Write}; +use std::os::unix::io::{FromRawFd, RawFd}; +use vhdx::vhdx::Vhdx; + +// Populate the corpus directory with a test file: +// truncate -s 16M /tmp/source +// qemu-img convert -O vhdx /tmp/source fuzz/corpus/vhdx/test.vhdx +// Run with: +// cargo fuzz run vhdx -j 32 -- -max_len=16777216 +fuzz_target!(|bytes| { + let shm = memfd_create(&ffi::CString::new("fuzz").unwrap(), 0).unwrap(); + let mut disk_file: File = unsafe { File::from_raw_fd(shm) }; + disk_file.write_all(&bytes[..]).unwrap(); + disk_file.seek(SeekFrom::Start(0)).unwrap(); + + if let Ok(mut vhdx) = Vhdx::new(disk_file) { + if vhdx.seek(SeekFrom::Start(0)).is_ok() { + let mut offset = 0; + while offset < bytes.len() { + let mut data = vec![0; 8192]; + vhdx.read_exact(&mut data).ok(); + offset += data.len(); + } + } + + if vhdx.seek(SeekFrom::Start(0)).is_ok() { + let mut offset = 0; + while offset < bytes.len() { + let data = vec![0; 8192]; + vhdx.write_all(&data).ok(); + offset += data.len(); + } + } + } +}); + +fn memfd_create(name: &ffi::CStr, flags: u32) -> Result { + let res = unsafe { libc::syscall(libc::SYS_memfd_create, name.as_ptr(), flags) }; + + if res < 0 { + Err(io::Error::last_os_error()) + } else { + Ok(res as RawFd) + } +}