From 67ea300221b2b9f2f3f8f97455350623f3038c59 Mon Sep 17 00:00:00 2001 From: Andrew Brown Date: Wed, 24 Aug 2022 11:19:56 -0700 Subject: [PATCH 1/2] [fuzz] Simplify macros used by single-instruction generator This removes the multiple macros used previously to describe the WebAssembly instruction signatures and replaces them with a single one--`inst!`. --- .../src/generators/single_inst_module.rs | 319 ++++++++---------- 1 file changed, 141 insertions(+), 178 deletions(-) diff --git a/crates/fuzzing/src/generators/single_inst_module.rs b/crates/fuzzing/src/generators/single_inst_module.rs index 6e1c193d3431..b2bed7983485 100644 --- a/crates/fuzzing/src/generators/single_inst_module.rs +++ b/crates/fuzzing/src/generators/single_inst_module.rs @@ -105,205 +105,168 @@ macro_rules! valtype { }; } -macro_rules! binary { - ($inst:ident, $rust_ty:tt) => { - binary! { $inst, $rust_ty, $rust_ty } +macro_rules! inst { + ($inst:ident, ($($arguments_ty:tt),+) -> $result_ty:tt) => { + inst! { $inst, ($($arguments_ty),+) -> $result_ty, |_| true } }; - ($inst:ident, $arguments_ty:tt, $result_ty:tt) => { + ($inst:ident, ($($arguments_ty:tt),+) -> $result_ty:tt, $feature:expr) => { SingleInstModule { instruction: Instruction::$inst, - parameters: &[valtype!($arguments_ty), valtype!($arguments_ty)], - results: &[valtype!($result_ty)], - feature: |_| true, - } - }; -} - -macro_rules! compare { - ($inst:ident, $rust_ty:tt) => { - binary! { $inst, $rust_ty, i32 } - }; -} - -macro_rules! unary { - ($inst:ident, $rust_ty:tt) => { - unary! { $inst, $rust_ty, $rust_ty } - }; - ($inst:ident, $argument_ty:tt, $result_ty:tt) => { - SingleInstModule { - instruction: Instruction::$inst, - parameters: &[valtype!($argument_ty)], - results: &[valtype!($result_ty)], - feature: |_| true, - } - }; - ($inst:ident, $argument_ty:tt, $result_ty:tt, $feature:expr) => { - SingleInstModule { - instruction: Instruction::$inst, - parameters: &[valtype!($argument_ty)], + parameters: &[$(valtype!($arguments_ty)),+], results: &[valtype!($result_ty)], feature: $feature, } }; } -macro_rules! convert { - ($inst:ident, $from_ty:tt -> $to_ty:tt) => { - unary! { $inst, $from_ty, $to_ty } - }; - ($inst:ident, $from_ty:tt -> $to_ty:tt, $feature:expr) => { - unary! { $inst, $from_ty, $to_ty, $feature } - }; -} - static INSTRUCTIONS: &[SingleInstModule] = &[ // Integer arithmetic. // I32Const // I64Const // F32Const // F64Const - unary!(I32Clz, i32), - unary!(I64Clz, i64), - unary!(I32Ctz, i32), - unary!(I64Ctz, i64), - unary!(I32Popcnt, i32), - unary!(I64Popcnt, i64), - binary!(I32Add, i32), - binary!(I64Add, i64), - binary!(I32Sub, i32), - binary!(I64Sub, i64), - binary!(I32Mul, i32), - binary!(I64Mul, i64), - binary!(I32DivS, i32), - binary!(I64DivS, i64), - binary!(I32DivU, i32), - binary!(I64DivU, i64), - binary!(I32RemS, i32), - binary!(I64RemS, i64), - binary!(I32RemU, i32), - binary!(I64RemU, i64), + inst!(I32Clz, (i32) -> i32), + inst!(I64Clz, (i64) -> i64), + inst!(I32Ctz, (i32) -> i32), + inst!(I64Ctz, (i64) -> i64), + inst!(I32Popcnt, (i32) -> i32), + inst!(I64Popcnt, (i64) -> i64), + inst!(I32Add, (i32, i32) -> i32), + inst!(I64Add, (i64, i64) -> i64), + inst!(I32Sub, (i32, i32) -> i32), + inst!(I64Sub, (i64, i64) -> i64), + inst!(I32Mul, (i32, i32) -> i32), + inst!(I64Mul, (i64, i64) -> i64), + inst!(I32DivS, (i32, i32) -> i32), + inst!(I64DivS, (i64, i64) -> i64), + inst!(I32DivU, (i32, i32) -> i32), + inst!(I64DivU, (i64, i64) -> i64), + inst!(I32RemS, (i32, i32) -> i32), + inst!(I64RemS, (i64, i64) -> i64), + inst!(I32RemU, (i32, i32) -> i32), + inst!(I64RemU, (i64, i64) -> i64), // Integer bitwise. - binary!(I32And, i32), - binary!(I64And, i64), - binary!(I32Or, i32), - binary!(I64Or, i64), - binary!(I32Xor, i32), - binary!(I64Xor, i64), - binary!(I32Shl, i32), - binary!(I64Shl, i64), - binary!(I32ShrS, i32), - binary!(I64ShrS, i64), - binary!(I32ShrU, i32), - binary!(I64ShrU, i64), - binary!(I32Rotl, i32), - binary!(I64Rotl, i64), - binary!(I32Rotr, i32), - binary!(I64Rotr, i64), + inst!(I32And, (i32, i32) -> i32), + inst!(I64And, (i64, i64) -> i64), + inst!(I32Or, (i32, i32) -> i32), + inst!(I64Or, (i64, i64) -> i64), + inst!(I32Xor, (i32, i32) -> i32), + inst!(I64Xor, (i64, i64) -> i64), + inst!(I32Shl, (i32, i32) -> i32), + inst!(I64Shl, (i64, i64) -> i64), + inst!(I32ShrS, (i32, i32) -> i32), + inst!(I64ShrS, (i64, i64) -> i64), + inst!(I32ShrU, (i32, i32) -> i32), + inst!(I64ShrU, (i64, i64) -> i64), + inst!(I32Rotl, (i32, i32) -> i32), + inst!(I64Rotl, (i64, i64) -> i64), + inst!(I32Rotr, (i32, i32) -> i32), + inst!(I64Rotr, (i64, i64) -> i64), // Integer comparison. - unary!(I32Eqz, i32), - unary!(I64Eqz, i64, i32), - compare!(I32Eq, i32), - compare!(I64Eq, i64), - compare!(I32Ne, i32), - compare!(I64Ne, i64), - compare!(I32LtS, i32), - compare!(I64LtS, i64), - compare!(I32LtU, i32), - compare!(I64LtU, i64), - compare!(I32GtS, i32), - compare!(I64GtS, i64), - compare!(I32GtU, i32), - compare!(I64GtU, i64), - compare!(I32LeS, i32), - compare!(I64LeS, i64), - compare!(I32LeU, i32), - compare!(I64LeU, i64), - compare!(I32GeS, i32), - compare!(I64GeS, i64), - compare!(I32GeU, i32), - compare!(I64GeU, i64), + inst!(I32Eqz, (i32) -> i32), + inst!(I64Eqz, (i64) -> i32), + inst!(I32Eq, (i32, i32) -> i32), + inst!(I64Eq, (i64, i64) -> i32), + inst!(I32Ne, (i32, i32) -> i32), + inst!(I64Ne, (i64, i64) -> i32), + inst!(I32LtS, (i32, i32) -> i32), + inst!(I64LtS, (i64, i64) -> i32), + inst!(I32LtU, (i32, i32) -> i32), + inst!(I64LtU, (i64, i64) -> i32), + inst!(I32GtS, (i32, i32) -> i32), + inst!(I64GtS, (i64, i64) -> i32), + inst!(I32GtU, (i32, i32) -> i32), + inst!(I64GtU, (i64, i64) -> i32), + inst!(I32LeS, (i32, i32) -> i32), + inst!(I64LeS, (i64, i64) -> i32), + inst!(I32LeU, (i32, i32) -> i32), + inst!(I64LeU, (i64, i64) -> i32), + inst!(I32GeS, (i32, i32) -> i32), + inst!(I64GeS, (i64, i64) -> i32), + inst!(I32GeU, (i32, i32) -> i32), + inst!(I64GeU, (i64, i64) -> i32), // Floating-point arithmetic. - unary!(F32Abs, f32), - unary!(F64Abs, f64), - unary!(F32Sqrt, f32), - unary!(F64Sqrt, f64), - unary!(F32Ceil, f32), - unary!(F64Ceil, f64), - unary!(F32Floor, f32), - unary!(F64Floor, f64), - unary!(F32Trunc, f32), - unary!(F64Trunc, f64), - unary!(F32Nearest, f32), - unary!(F64Nearest, f64), - unary!(F32Neg, f32), - unary!(F64Neg, f64), - binary!(F32Add, f32), - binary!(F64Add, f64), - binary!(F32Sub, f32), - binary!(F64Sub, f64), - binary!(F32Mul, f32), - binary!(F64Mul, f64), - binary!(F32Div, f32), - binary!(F64Div, f64), - binary!(F32Min, f32), - binary!(F64Min, f64), - binary!(F32Max, f32), - binary!(F64Max, f64), - binary!(F32Copysign, f32), - binary!(F64Copysign, f64), + inst!(F32Abs, (f32) -> f32), + inst!(F64Abs, (f64) -> f64), + inst!(F32Sqrt, (f32) -> f32), + inst!(F64Sqrt, (f64) -> f64), + inst!(F32Ceil, (f32) -> f32), + inst!(F64Ceil, (f64) -> f64), + inst!(F32Floor, (f32) -> f32), + inst!(F64Floor, (f64) -> f64), + inst!(F32Trunc, (f32) -> f32), + inst!(F64Trunc, (f64) -> f64), + inst!(F32Nearest, (f32) -> f32), + inst!(F64Nearest, (f64) -> f64), + inst!(F32Neg, (f32) -> f32), + inst!(F64Neg, (f64) -> f64), + inst!(F32Add, (f32, f32) -> f32), + inst!(F64Add, (f64, f64) -> f64), + inst!(F32Sub, (f32, f32) -> f32), + inst!(F64Sub, (f64, f64) -> f64), + inst!(F32Mul, (f32, f32) -> f32), + inst!(F64Mul, (f64, f64) -> f64), + inst!(F32Div, (f32, f32) -> f32), + inst!(F64Div, (f64, f64) -> f64), + inst!(F32Min, (f32, f32) -> f32), + inst!(F64Min, (f64, f64) -> f64), + inst!(F32Max, (f32, f32) -> f32), + inst!(F64Max, (f64, f64) -> f64), + inst!(F32Copysign, (f32, f32) -> f32), + inst!(F64Copysign, (f64, f64) -> f64), // Floating-point comparison. - compare!(F32Eq, f32), - compare!(F64Eq, f64), - compare!(F32Ne, f32), - compare!(F64Ne, f64), - compare!(F32Lt, f32), - compare!(F64Lt, f64), - compare!(F32Gt, f32), - compare!(F64Gt, f64), - compare!(F32Le, f32), - compare!(F64Le, f64), - compare!(F32Ge, f32), - compare!(F64Ge, f64), + inst!(F32Eq, (f32, f32) -> i32), + inst!(F64Eq, (f64, f64) -> i32), + inst!(F32Ne, (f32, f32) -> i32), + inst!(F64Ne, (f64, f64) -> i32), + inst!(F32Lt, (f32, f32) -> i32), + inst!(F64Lt, (f64, f64) -> i32), + inst!(F32Gt, (f32, f32) -> i32), + inst!(F64Gt, (f64, f64) -> i32), + inst!(F32Le, (f32, f32) -> i32), + inst!(F64Le, (f64, f64) -> i32), + inst!(F32Ge, (f32, f32) -> i32), + inst!(F64Ge, (f64, f64) -> i32), // Integer conversions ("to integer"). - unary!(I32Extend8S, i32, i32, |c| c.config.sign_extension_enabled), - unary!(I32Extend16S, i32, i32, |c| c.config.sign_extension_enabled), - unary!(I64Extend8S, i64, i64, |c| c.config.sign_extension_enabled), - unary!(I64Extend16S, i64, i64, |c| c.config.sign_extension_enabled), - convert!(I64Extend32S, i64 -> i64, |c| c.config.sign_extension_enabled), - convert!(I32WrapI64, i64 -> i32), - convert!(I64ExtendI32S, i32 -> i64), - convert!(I64ExtendI32U, i32 -> i64), - convert!(I32TruncF32S, f32 -> i32), - convert!(I32TruncF32U, f32 -> i32), - convert!(I32TruncF64S, f64 -> i32), - convert!(I32TruncF64U, f64 -> i32), - convert!(I64TruncF32S, f32 -> i64), - convert!(I64TruncF32U, f32 -> i64), - convert!(I64TruncF64S, f64 -> i64), - convert!(I64TruncF64U, f64 -> i64), - convert!(I32TruncSatF32S, f32 -> i32, |c| c.config.saturating_float_to_int_enabled), - convert!(I32TruncSatF32U, f32 -> i32, |c| c.config.saturating_float_to_int_enabled), - convert!(I32TruncSatF64S, f64 -> i32, |c| c.config.saturating_float_to_int_enabled), - convert!(I32TruncSatF64U, f64 -> i32, |c| c.config.saturating_float_to_int_enabled), - convert!(I64TruncSatF32S, f32 -> i64, |c| c.config.saturating_float_to_int_enabled), - convert!(I64TruncSatF32U, f32 -> i64, |c| c.config.saturating_float_to_int_enabled), - convert!(I64TruncSatF64S, f64 -> i64, |c| c.config.saturating_float_to_int_enabled), - convert!(I64TruncSatF64U, f64 -> i64, |c| c.config.saturating_float_to_int_enabled), - convert!(I32ReinterpretF32, f32 -> i32), - convert!(I64ReinterpretF64, f64 -> i64), + inst!(I32Extend8S, (i32) -> i32, |c| c.config.sign_extension_enabled), + inst!(I32Extend16S, (i32) -> i32, |c| c.config.sign_extension_enabled), + inst!(I64Extend8S, (i64) -> i64, |c| c.config.sign_extension_enabled), + inst!(I64Extend16S, (i64) -> i64, |c| c.config.sign_extension_enabled), + inst!(I64Extend32S, (i64) -> i64, |c| c.config.sign_extension_enabled), + inst!(I32WrapI64, (i64) -> i32), + inst!(I64ExtendI32S, (i32) -> i64), + inst!(I64ExtendI32U, (i32) -> i64), + inst!(I32TruncF32S, (f32) -> i32), + inst!(I32TruncF32U, (f32) -> i32), + inst!(I32TruncF64S, (f64) -> i32), + inst!(I32TruncF64U, (f64) -> i32), + inst!(I64TruncF32S, (f32) -> i64), + inst!(I64TruncF32U, (f32) -> i64), + inst!(I64TruncF64S, (f64) -> i64), + inst!(I64TruncF64U, (f64) -> i64), + inst!(I32TruncSatF32S, (f32) -> i32, |c| c.config.saturating_float_to_int_enabled), + inst!(I32TruncSatF32U, (f32) -> i32, |c| c.config.saturating_float_to_int_enabled), + inst!(I32TruncSatF64S, (f64) -> i32, |c| c.config.saturating_float_to_int_enabled), + inst!(I32TruncSatF64U, (f64) -> i32, |c| c.config.saturating_float_to_int_enabled), + inst!(I64TruncSatF32S, (f32) -> i64, |c| c.config.saturating_float_to_int_enabled), + inst!(I64TruncSatF32U, (f32) -> i64, |c| c.config.saturating_float_to_int_enabled), + inst!(I64TruncSatF64S, (f64) -> i64, |c| c.config.saturating_float_to_int_enabled), + inst!(I64TruncSatF64U, (f64) -> i64, |c| c.config.saturating_float_to_int_enabled), + inst!(I32ReinterpretF32, (f32) -> i32), + inst!(I64ReinterpretF64, (f64) -> i64), // Floating-point conversions ("to float"). - convert!(F32DemoteF64, f64 -> f32), - convert!(F64PromoteF32, f32 -> f64), - convert!(F32ConvertI32S, i32 -> f32), - convert!(F32ConvertI32U, i32 -> f32), - convert!(F32ConvertI64S, i64 -> f32), - convert!(F32ConvertI64U, i64 -> f32), - convert!(F64ConvertI32S, i32 -> f64), - convert!(F64ConvertI32U, i32 -> f64), - convert!(F64ConvertI64S, i64 -> f64), - convert!(F64ConvertI64U, i64 -> f64), - convert!(F32ReinterpretI32, i32 -> f32), - convert!(F64ReinterpretI64, i64 -> f64), + inst!(F32DemoteF64, (f64) -> f32), + inst!(F64PromoteF32, (f32) -> f64), + inst!(F32ConvertI32S, (i32) -> f32), + inst!(F32ConvertI32U, (i32) -> f32), + inst!(F32ConvertI64S, (i64) -> f32), + inst!(F32ConvertI64U, (i64) -> f32), + inst!(F64ConvertI32S, (i32) -> f64), + inst!(F64ConvertI32U, (i32) -> f64), + inst!(F64ConvertI64S, (i64) -> f64), + inst!(F64ConvertI64U, (i64) -> f64), + inst!(F32ReinterpretI32, (i32) -> f32), + inst!(F64ReinterpretI64, (i64) -> f64), ]; #[cfg(test)] From 92b55255d4a0dc18565529b4cd6614b007c6d609 Mon Sep 17 00:00:00 2001 From: Andrew Brown Date: Wed, 24 Aug 2022 12:35:19 -0700 Subject: [PATCH 2/2] review: allow 0-argument instructions --- crates/fuzzing/src/generators/single_inst_module.rs | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/crates/fuzzing/src/generators/single_inst_module.rs b/crates/fuzzing/src/generators/single_inst_module.rs index b2bed7983485..ee156610d930 100644 --- a/crates/fuzzing/src/generators/single_inst_module.rs +++ b/crates/fuzzing/src/generators/single_inst_module.rs @@ -106,13 +106,13 @@ macro_rules! valtype { } macro_rules! inst { - ($inst:ident, ($($arguments_ty:tt),+) -> $result_ty:tt) => { - inst! { $inst, ($($arguments_ty),+) -> $result_ty, |_| true } + ($inst:ident, ($($arguments_ty:tt),*) -> $result_ty:tt) => { + inst! { $inst, ($($arguments_ty),*) -> $result_ty, |_| true } }; - ($inst:ident, ($($arguments_ty:tt),+) -> $result_ty:tt, $feature:expr) => { + ($inst:ident, ($($arguments_ty:tt),*) -> $result_ty:tt, $feature:expr) => { SingleInstModule { instruction: Instruction::$inst, - parameters: &[$(valtype!($arguments_ty)),+], + parameters: &[$(valtype!($arguments_ty)),*], results: &[valtype!($result_ty)], feature: $feature, }