From 4134f7d64b4f34830b2977242ccdbd7f6b942929 Mon Sep 17 00:00:00 2001 From: Sergej Schumilo Date: Wed, 8 Dec 2021 18:25:52 +0100 Subject: [PATCH] add config option to enable hypervisor-assisted write protection of the input buffer --- config/src/config.rs | 4 +++- config/src/loader.rs | 7 +++++++ fuzz_runner/src/nyx/mod.rs | 7 +++++-- fuzz_runner/src/nyx/params.rs | 5 +++++ fuzz_runner/src/nyx/qemu_process.rs | 8 +++++++- 5 files changed, 27 insertions(+), 4 deletions(-) diff --git a/config/src/config.rs b/config/src/config.rs index 604b181..25f93e8 100644 --- a/config/src/config.rs +++ b/config/src/config.rs @@ -129,7 +129,8 @@ pub struct FuzzerConfig { pub dict: Vec>, pub snapshot_placement: SnapshotPlacement, pub dump_python_code_for_inputs: Option, - pub exit_after_first_crash: bool + pub exit_after_first_crash: bool, + pub write_protected_input_buffer: bool, } impl FuzzerConfig{ pub fn new_from_loader(sharedir: &str, default: FuzzerConfigLoader, config: FuzzerConfigLoader) -> Self { @@ -157,6 +158,7 @@ impl FuzzerConfig{ snapshot_placement: config.snapshot_placement.or(default.snapshot_placement).expect("no snapshot_placement specified"), dump_python_code_for_inputs: config.dump_python_code_for_inputs.or(default.dump_python_code_for_inputs), exit_after_first_crash: config.exit_after_first_crash.unwrap_or(default.exit_after_first_crash.unwrap_or(false)), + write_protected_input_buffer: config.write_protected_input_buffer, } } } diff --git a/config/src/loader.rs b/config/src/loader.rs index 115577d..4cd6be9 100644 --- a/config/src/loader.rs +++ b/config/src/loader.rs @@ -36,6 +36,9 @@ pub enum FuzzRunnerConfigLoader { #[derive(Clone, Serialize, Deserialize)] pub struct FuzzerConfigLoader { + #[serde(default = "default_write_protected_input_buffer")] + pub write_protected_input_buffer: bool, + pub workdir_path: Option, pub bitmap_size: Option, pub mem_limit: Option, @@ -51,6 +54,10 @@ pub struct FuzzerConfigLoader { pub exit_after_first_crash: Option, } +fn default_write_protected_input_buffer() -> bool { + false +} + #[derive(Clone, Serialize, Deserialize)] pub struct ConfigLoader { pub include_default_config_path: Option, diff --git a/fuzz_runner/src/nyx/mod.rs b/fuzz_runner/src/nyx/mod.rs index f452769..fccadd2 100644 --- a/fuzz_runner/src/nyx/mod.rs +++ b/fuzz_runner/src/nyx/mod.rs @@ -36,7 +36,8 @@ pub fn qemu_process_new_from_kernel(sharedir: String, cfg: &QemuKernelConfig, fu dump_python_code_for_inputs: match fuzz_cfg.dump_python_code_for_inputs{ None => false, Some(x) => x, - } + }, + write_protected_input_buffer: fuzz_cfg.write_protected_input_buffer, }; let qemu_id = fuzz_cfg.thread_id; let qemu_params = params::QemuParams::new_from_kernel(&fuzz_cfg.workdir_path, qemu_id, ¶ms, fuzz_cfg.threads > 1); @@ -75,7 +76,8 @@ pub fn qemu_process_new_from_snapshot(sharedir: String, cfg: &QemuSnapshotConfig dump_python_code_for_inputs: match fuzz_cfg.dump_python_code_for_inputs{ None => false, Some(x) => x, - } + }, + write_protected_input_buffer: fuzz_cfg.write_protected_input_buffer, }; let qemu_id = fuzz_cfg.thread_id; let qemu_params = params::QemuParams::new_from_snapshot(&fuzz_cfg.workdir_path, qemu_id, fuzz_cfg.cpu_pin_start_at, ¶ms, fuzz_cfg.threads > 1); @@ -113,6 +115,7 @@ mod tests { bitmap_size: 0x1 << 16, debug: false, dump_python_code_for_inputs: false, + write_protected_input_buffer: false, }; let qemu_id = 1; let qemu_params = QemuParams::new_from_kernel(workdir, qemu_id, ¶ms); diff --git a/fuzz_runner/src/nyx/params.rs b/fuzz_runner/src/nyx/params.rs index 8c5f3f4..88e69dd 100644 --- a/fuzz_runner/src/nyx/params.rs +++ b/fuzz_runner/src/nyx/params.rs @@ -11,6 +11,7 @@ pub struct KernelVmParams { pub debug: bool, pub dump_python_code_for_inputs: bool, + pub write_protected_input_buffer: bool, } pub struct SnapshotVmParams{ @@ -24,6 +25,7 @@ pub struct SnapshotVmParams{ pub debug: bool, pub dump_python_code_for_inputs: bool, + pub write_protected_input_buffer: bool, } pub struct QemuParams { @@ -39,6 +41,7 @@ pub struct QemuParams { pub payload_size: usize, pub dump_python_code_for_inputs: bool, + pub write_protected_input_buffer: bool, } impl QemuParams { @@ -152,6 +155,7 @@ impl QemuParams { bitmap_size: params.bitmap_size, payload_size: (1 << 16), dump_python_code_for_inputs: params.dump_python_code_for_inputs, + write_protected_input_buffer: params.write_protected_input_buffer, }; } @@ -261,6 +265,7 @@ impl QemuParams { bitmap_size: params.bitmap_size, payload_size: (128 << 10), dump_python_code_for_inputs: params.dump_python_code_for_inputs, + write_protected_input_buffer: params.write_protected_input_buffer, }; } } diff --git a/fuzz_runner/src/nyx/qemu_process.rs b/fuzz_runner/src/nyx/qemu_process.rs index 2fd7e63..de61095 100644 --- a/fuzz_runner/src/nyx/qemu_process.rs +++ b/fuzz_runner/src/nyx/qemu_process.rs @@ -176,7 +176,13 @@ impl QemuProcess { let mut aux_buffer = AuxBuffer::new(aux_shm_f); aux_buffer.validate_header(); - aux_buffer.config.protect_payload_buffer = 1; + if params.write_protected_input_buffer{ + if params.qemu_id == 0 { + println!("[!] libnyx: input buffer is write protected"); + } + aux_buffer.config.protect_payload_buffer = 1; + aux_buffer.config.changed = 1; + } loop { if aux_buffer.result.hprintf == 1 {