diff options
-rwxr-xr-x | ci/script.sh | 2 | ||||
-rw-r--r-- | tests/expectations/tests/issue-816.rs | 808 | ||||
-rw-r--r-- | tests/headers/issue-816.h | 49 | ||||
-rw-r--r-- | tests/quickchecking/Cargo.toml | 14 | ||||
-rw-r--r-- | tests/quickchecking/src/bin.rs | 110 | ||||
-rw-r--r-- | tests/quickchecking/src/lib.rs | 98 | ||||
-rw-r--r-- | tests/quickchecking/tests/fuzzed-c-headers.rs | 151 |
7 files changed, 1162 insertions, 70 deletions
diff --git a/ci/script.sh b/ci/script.sh index b9e75892..91ea7c13 100755 --- a/ci/script.sh +++ b/ci/script.sh @@ -41,7 +41,7 @@ case "$BINDGEN_JOB" in "quickchecking") cd ./tests/quickchecking # TODO: Actually run quickchecks once `bindgen` is reliable enough. - cargo check + cargo test ;; *) echo "Error! Unknown \$BINDGEN_JOB: '$BINDGEN_JOB'" diff --git a/tests/expectations/tests/issue-816.rs b/tests/expectations/tests/issue-816.rs new file mode 100644 index 00000000..bb8a323a --- /dev/null +++ b/tests/expectations/tests/issue-816.rs @@ -0,0 +1,808 @@ +/* automatically generated by rust-bindgen */ + + +#![allow(dead_code, non_snake_case, non_camel_case_types, non_upper_case_globals)] + + +#[repr(C)] +#[derive(Copy, Clone, Debug, Default, Eq, Hash, Ord, PartialEq, PartialOrd)] +pub struct __BindgenBitfieldUnit<Storage, Align> +where + Storage: AsRef<[u8]> + AsMut<[u8]>, +{ + storage: Storage, + align: [Align; 0], +} + +impl<Storage, Align> __BindgenBitfieldUnit<Storage, Align> +where + Storage: AsRef<[u8]> + AsMut<[u8]>, +{ + #[inline] + pub fn new(storage: Storage) -> Self { + Self { storage, align: [] } + } + + #[inline] + pub fn get_bit(&self, index: usize) -> bool { + debug_assert!(index / 8 < self.storage.as_ref().len()); + + let byte_index = index / 8; + let byte = self.storage.as_ref()[byte_index]; + + let bit_index = index % 8; + let mask = 1 << bit_index; + + byte & mask == mask + } + + #[inline] + pub fn set_bit(&mut self, index: usize, val: bool) { + debug_assert!(index / 8 < self.storage.as_ref().len()); + + let byte_index = index / 8; + let byte = &mut self.storage.as_mut()[byte_index]; + + let bit_index = index % 8; + let mask = 1 << bit_index; + + if val { + *byte |= mask; + } else { + *byte &= !mask; + } + } + + #[inline] + pub fn get(&self, bit_offset: usize, bit_width: u8) -> u64 { + debug_assert!(bit_width <= 64); + debug_assert!(bit_offset / 8 < self.storage.as_ref().len()); + debug_assert!((bit_offset + (bit_width as usize)) / 8 <= self.storage.as_ref().len()); + + let mut val = 0; + + for i in 0..(bit_width as usize) { + if self.get_bit(i + bit_offset) { + val |= 1 << i; + } + } + + val + } + + #[inline] + pub fn set(&mut self, bit_offset: usize, bit_width: u8, val: u64) { + debug_assert!(bit_width <= 64); + debug_assert!(bit_offset / 8 < self.storage.as_ref().len()); + debug_assert!((bit_offset + (bit_width as usize)) / 8 <= self.storage.as_ref().len()); + + for i in 0..(bit_width as usize) { + let mask = 1 << i; + let val_bit_is_set = val & mask == mask; + self.set_bit(i + bit_offset, val_bit_is_set); + } + } +} +#[repr(C)] +#[derive(Debug, Default, Copy, Clone)] +pub struct jvmtiCapabilities { + pub _bitfield_1: __BindgenBitfieldUnit<[u8; 16usize], u8>, + pub __bindgen_align: [u32; 0usize], +} +#[test] +fn bindgen_test_layout_jvmtiCapabilities() { + assert_eq!( + ::std::mem::size_of::<jvmtiCapabilities>(), + 16usize, + concat!("Size of: ", stringify!(jvmtiCapabilities)) + ); + assert_eq!( + ::std::mem::align_of::<jvmtiCapabilities>(), + 4usize, + concat!("Alignment of ", stringify!(jvmtiCapabilities)) + ); +} +impl jvmtiCapabilities { + #[inline] + pub fn can_tag_objects(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(0usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_tag_objects(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(0usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_field_modification_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(1usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_field_modification_events(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(1usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_field_access_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(2usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_field_access_events(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(2usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_get_bytecodes(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(3usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_get_bytecodes(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(3usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_get_synthetic_attribute(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(4usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_get_synthetic_attribute(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(4usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_get_owned_monitor_info(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(5usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_get_owned_monitor_info(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(5usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_get_current_contended_monitor(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(6usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_get_current_contended_monitor(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(6usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_get_monitor_info(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(7usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_get_monitor_info(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(7usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_pop_frame(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(8usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_pop_frame(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(8usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_redefine_classes(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(9usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_redefine_classes(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(9usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_signal_thread(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(10usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_signal_thread(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(10usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_get_source_file_name(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(11usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_get_source_file_name(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(11usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_get_line_numbers(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(12usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_get_line_numbers(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(12usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_get_source_debug_extension(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(13usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_get_source_debug_extension(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(13usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_access_local_variables(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(14usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_access_local_variables(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(14usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_maintain_original_method_order(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(15usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_maintain_original_method_order(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(15usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_single_step_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(16usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_single_step_events(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(16usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_exception_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(17usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_exception_events(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(17usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_frame_pop_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(18usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_frame_pop_events(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(18usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_breakpoint_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(19usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_breakpoint_events(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(19usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_suspend(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(20usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_suspend(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(20usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_redefine_any_class(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(21usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_redefine_any_class(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(21usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_get_current_thread_cpu_time(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(22usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_get_current_thread_cpu_time(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(22usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_get_thread_cpu_time(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(23usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_get_thread_cpu_time(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(23usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_method_entry_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(24usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_method_entry_events(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(24usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_method_exit_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(25usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_method_exit_events(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(25usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_all_class_hook_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(26usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_all_class_hook_events(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(26usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_compiled_method_load_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(27usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_compiled_method_load_events(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(27usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_monitor_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(28usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_monitor_events(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(28usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_vm_object_alloc_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(29usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_vm_object_alloc_events(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(29usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_native_method_bind_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(30usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_native_method_bind_events(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(30usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_garbage_collection_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(31usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_garbage_collection_events(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(31usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_object_free_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(32usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_object_free_events(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(32usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_force_early_return(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(33usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_force_early_return(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(33usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_get_owned_monitor_stack_depth_info(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(34usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_get_owned_monitor_stack_depth_info(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(34usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_get_constant_pool(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(35usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_get_constant_pool(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(35usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_set_native_method_prefix(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(36usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_set_native_method_prefix(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(36usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_retransform_classes(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(37usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_retransform_classes(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(37usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_retransform_any_class(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(38usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_retransform_any_class(&mut self, val: ::std::os::raw::c_uint) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(38usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_resource_exhaustion_heap_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(39usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_resource_exhaustion_heap_events( + &mut self, + val: ::std::os::raw::c_uint, + ) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(39usize, 1u8, val as u64) + } + } + #[inline] + pub fn can_generate_resource_exhaustion_threads_events(&self) -> ::std::os::raw::c_uint { + unsafe { ::std::mem::transmute(self._bitfield_1.get(40usize, 1u8) as u32) } + } + #[inline] + pub fn set_can_generate_resource_exhaustion_threads_events( + &mut self, + val: ::std::os::raw::c_uint, + ) { + unsafe { + let val: u32 = ::std::mem::transmute(val); + self._bitfield_1.set(40usize, 1u8, val as u64) + } + } + #[inline] + pub fn new_bitfield_1( + can_tag_objects: ::std::os::raw::c_uint, + can_generate_field_modification_events: ::std::os::raw::c_uint, + can_generate_field_access_events: ::std::os::raw::c_uint, + can_get_bytecodes: ::std::os::raw::c_uint, + can_get_synthetic_attribute: ::std::os::raw::c_uint, + can_get_owned_monitor_info: ::std::os::raw::c_uint, + can_get_current_contended_monitor: ::std::os::raw::c_uint, + can_get_monitor_info: ::std::os::raw::c_uint, + can_pop_frame: ::std::os::raw::c_uint, + can_redefine_classes: ::std::os::raw::c_uint, + can_signal_thread: ::std::os::raw::c_uint, + can_get_source_file_name: ::std::os::raw::c_uint, + can_get_line_numbers: ::std::os::raw::c_uint, + can_get_source_debug_extension: ::std::os::raw::c_uint, + can_access_local_variables: ::std::os::raw::c_uint, + can_maintain_original_method_order: ::std::os::raw::c_uint, + can_generate_single_step_events: ::std::os::raw::c_uint, + can_generate_exception_events: ::std::os::raw::c_uint, + can_generate_frame_pop_events: ::std::os::raw::c_uint, + can_generate_breakpoint_events: ::std::os::raw::c_uint, + can_suspend: ::std::os::raw::c_uint, + can_redefine_any_class: ::std::os::raw::c_uint, + can_get_current_thread_cpu_time: ::std::os::raw::c_uint, + can_get_thread_cpu_time: ::std::os::raw::c_uint, + can_generate_method_entry_events: ::std::os::raw::c_uint, + can_generate_method_exit_events: ::std::os::raw::c_uint, + can_generate_all_class_hook_events: ::std::os::raw::c_uint, + can_generate_compiled_method_load_events: ::std::os::raw::c_uint, + can_generate_monitor_events: ::std::os::raw::c_uint, + can_generate_vm_object_alloc_events: ::std::os::raw::c_uint, + can_generate_native_method_bind_events: ::std::os::raw::c_uint, + can_generate_garbage_collection_events: ::std::os::raw::c_uint, + can_generate_object_free_events: ::std::os::raw::c_uint, + can_force_early_return: ::std::os::raw::c_uint, + can_get_owned_monitor_stack_depth_info: ::std::os::raw::c_uint, + can_get_constant_pool: ::std::os::raw::c_uint, + can_set_native_method_prefix: ::std::os::raw::c_uint, + can_retransform_classes: ::std::os::raw::c_uint, + can_retransform_any_class: ::std::os::raw::c_uint, + can_generate_resource_exhaustion_heap_events: ::std::os::raw::c_uint, + can_generate_resource_exhaustion_threads_events: ::std::os::raw::c_uint, + ) -> __BindgenBitfieldUnit<[u8; 16usize], u8> { + let mut __bindgen_bitfield_unit: __BindgenBitfieldUnit<[u8; 16usize], u8> = + Default::default(); + __bindgen_bitfield_unit.set(0usize, 1u8, { + let can_tag_objects: u32 = unsafe { ::std::mem::transmute(can_tag_objects) }; + can_tag_objects as u64 + }); + __bindgen_bitfield_unit.set(1usize, 1u8, { + let can_generate_field_modification_events: u32 = + unsafe { ::std::mem::transmute(can_generate_field_modification_events) }; + can_generate_field_modification_events as u64 + }); + __bindgen_bitfield_unit.set(2usize, 1u8, { + let can_generate_field_access_events: u32 = + unsafe { ::std::mem::transmute(can_generate_field_access_events) }; + can_generate_field_access_events as u64 + }); + __bindgen_bitfield_unit.set(3usize, 1u8, { + let can_get_bytecodes: u32 = unsafe { ::std::mem::transmute(can_get_bytecodes) }; + can_get_bytecodes as u64 + }); + __bindgen_bitfield_unit.set(4usize, 1u8, { + let can_get_synthetic_attribute: u32 = + unsafe { ::std::mem::transmute(can_get_synthetic_attribute) }; + can_get_synthetic_attribute as u64 + }); + __bindgen_bitfield_unit.set(5usize, 1u8, { + let can_get_owned_monitor_info: u32 = + unsafe { ::std::mem::transmute(can_get_owned_monitor_info) }; + can_get_owned_monitor_info as u64 + }); + __bindgen_bitfield_unit.set(6usize, 1u8, { + let can_get_current_contended_monitor: u32 = + unsafe { ::std::mem::transmute(can_get_current_contended_monitor) }; + can_get_current_contended_monitor as u64 + }); + __bindgen_bitfield_unit.set(7usize, 1u8, { + let can_get_monitor_info: u32 = unsafe { ::std::mem::transmute(can_get_monitor_info) }; + can_get_monitor_info as u64 + }); + __bindgen_bitfield_unit.set(8usize, 1u8, { + let can_pop_frame: u32 = unsafe { ::std::mem::transmute(can_pop_frame) }; + can_pop_frame as u64 + }); + __bindgen_bitfield_unit.set(9usize, 1u8, { + let can_redefine_classes: u32 = unsafe { ::std::mem::transmute(can_redefine_classes) }; + can_redefine_classes as u64 + }); + __bindgen_bitfield_unit.set(10usize, 1u8, { + let can_signal_thread: u32 = unsafe { ::std::mem::transmute(can_signal_thread) }; + can_signal_thread as u64 + }); + __bindgen_bitfield_unit.set(11usize, 1u8, { + let can_get_source_file_name: u32 = + unsafe { ::std::mem::transmute(can_get_source_file_name) }; + can_get_source_file_name as u64 + }); + __bindgen_bitfield_unit.set(12usize, 1u8, { + let can_get_line_numbers: u32 = unsafe { ::std::mem::transmute(can_get_line_numbers) }; + can_get_line_numbers as u64 + }); + __bindgen_bitfield_unit.set(13usize, 1u8, { + let can_get_source_debug_extension: u32 = + unsafe { ::std::mem::transmute(can_get_source_debug_extension) }; + can_get_source_debug_extension as u64 + }); + __bindgen_bitfield_unit.set(14usize, 1u8, { + let can_access_local_variables: u32 = + unsafe { ::std::mem::transmute(can_access_local_variables) }; + can_access_local_variables as u64 + }); + __bindgen_bitfield_unit.set(15usize, 1u8, { + let can_maintain_original_method_order: u32 = + unsafe { ::std::mem::transmute(can_maintain_original_method_order) }; + can_maintain_original_method_order as u64 + }); + __bindgen_bitfield_unit.set(16usize, 1u8, { + let can_generate_single_step_events: u32 = + unsafe { ::std::mem::transmute(can_generate_single_step_events) }; + can_generate_single_step_events as u64 + }); + __bindgen_bitfield_unit.set(17usize, 1u8, { + let can_generate_exception_events: u32 = + unsafe { ::std::mem::transmute(can_generate_exception_events) }; + can_generate_exception_events as u64 + }); + __bindgen_bitfield_unit.set(18usize, 1u8, { + let can_generate_frame_pop_events: u32 = + unsafe { ::std::mem::transmute(can_generate_frame_pop_events) }; + can_generate_frame_pop_events as u64 + }); + __bindgen_bitfield_unit.set(19usize, 1u8, { + let can_generate_breakpoint_events: u32 = + unsafe { ::std::mem::transmute(can_generate_breakpoint_events) }; + can_generate_breakpoint_events as u64 + }); + __bindgen_bitfield_unit.set(20usize, 1u8, { + let can_suspend: u32 = unsafe { ::std::mem::transmute(can_suspend) }; + can_suspend as u64 + }); + __bindgen_bitfield_unit.set(21usize, 1u8, { + let can_redefine_any_class: u32 = + unsafe { ::std::mem::transmute(can_redefine_any_class) }; + can_redefine_any_class as u64 + }); + __bindgen_bitfield_unit.set(22usize, 1u8, { + let can_get_current_thread_cpu_time: u32 = + unsafe { ::std::mem::transmute(can_get_current_thread_cpu_time) }; + can_get_current_thread_cpu_time as u64 + }); + __bindgen_bitfield_unit.set(23usize, 1u8, { + let can_get_thread_cpu_time: u32 = + unsafe { ::std::mem::transmute(can_get_thread_cpu_time) }; + can_get_thread_cpu_time as u64 + }); + __bindgen_bitfield_unit.set(24usize, 1u8, { + let can_generate_method_entry_events: u32 = + unsafe { ::std::mem::transmute(can_generate_method_entry_events) }; + can_generate_method_entry_events as u64 + }); + __bindgen_bitfield_unit.set(25usize, 1u8, { + let can_generate_method_exit_events: u32 = + unsafe { ::std::mem::transmute(can_generate_method_exit_events) }; + can_generate_method_exit_events as u64 + }); + __bindgen_bitfield_unit.set(26usize, 1u8, { + let can_generate_all_class_hook_events: u32 = + unsafe { ::std::mem::transmute(can_generate_all_class_hook_events) }; + can_generate_all_class_hook_events as u64 + }); + __bindgen_bitfield_unit.set(27usize, 1u8, { + let can_generate_compiled_method_load_events: u32 = + unsafe { ::std::mem::transmute(can_generate_compiled_method_load_events) }; + can_generate_compiled_method_load_events as u64 + }); + __bindgen_bitfield_unit.set(28usize, 1u8, { + let can_generate_monitor_events: u32 = + unsafe { ::std::mem::transmute(can_generate_monitor_events) }; + can_generate_monitor_events as u64 + }); + __bindgen_bitfield_unit.set(29usize, 1u8, { + let can_generate_vm_object_alloc_events: u32 = + unsafe { ::std::mem::transmute(can_generate_vm_object_alloc_events) }; + can_generate_vm_object_alloc_events as u64 + }); + __bindgen_bitfield_unit.set(30usize, 1u8, { + let can_generate_native_method_bind_events: u32 = + unsafe { ::std::mem::transmute(can_generate_native_method_bind_events) }; + can_generate_native_method_bind_events as u64 + }); + __bindgen_bitfield_unit.set(31usize, 1u8, { + let can_generate_garbage_collection_events: u32 = + unsafe { ::std::mem::transmute(can_generate_garbage_collection_events) }; + can_generate_garbage_collection_events as u64 + }); + __bindgen_bitfield_unit.set(32usize, 1u8, { + let can_generate_object_free_events: u32 = + unsafe { ::std::mem::transmute(can_generate_object_free_events) }; + can_generate_object_free_events as u64 + }); + __bindgen_bitfield_unit.set(33usize, 1u8, { + let can_force_early_return: u32 = + unsafe { ::std::mem::transmute(can_force_early_return) }; + can_force_early_return as u64 + }); + __bindgen_bitfield_unit.set(34usize, 1u8, { + let can_get_owned_monitor_stack_depth_info: u32 = + unsafe { ::std::mem::transmute(can_get_owned_monitor_stack_depth_info) }; + can_get_owned_monitor_stack_depth_info as u64 + }); + __bindgen_bitfield_unit.set(35usize, 1u8, { + let can_get_constant_pool: u32 = + unsafe { ::std::mem::transmute(can_get_constant_pool) }; + can_get_constant_pool as u64 + }); + __bindgen_bitfield_unit.set(36usize, 1u8, { + let can_set_native_method_prefix: u32 = + unsafe { ::std::mem::transmute(can_set_native_method_prefix) }; + can_set_native_method_prefix as u64 + }); + __bindgen_bitfield_unit.set(37usize, 1u8, { + let can_retransform_classes: u32 = + unsafe { ::std::mem::transmute(can_retransform_classes) }; + can_retransform_classes as u64 + }); + __bindgen_bitfield_unit.set(38usize, 1u8, { + let can_retransform_any_class: u32 = + unsafe { ::std::mem::transmute(can_retransform_any_class) }; + can_retransform_any_class as u64 + }); + __bindgen_bitfield_unit.set(39usize, 1u8, { + let can_generate_resource_exhaustion_heap_events: u32 = + unsafe { ::std::mem::transmute(can_generate_resource_exhaustion_heap_events) }; + can_generate_resource_exhaustion_heap_events as u64 + }); + __bindgen_bitfield_unit.set(40usize, 1u8, { + let can_generate_resource_exhaustion_threads_events: u32 = + unsafe { ::std::mem::transmute(can_generate_resource_exhaustion_threads_events) }; + can_generate_resource_exhaustion_threads_events as u64 + }); + __bindgen_bitfield_unit + } +} diff --git a/tests/headers/issue-816.h b/tests/headers/issue-816.h new file mode 100644 index 00000000..cacb0260 --- /dev/null +++ b/tests/headers/issue-816.h @@ -0,0 +1,49 @@ +typedef struct { + unsigned int can_tag_objects : 1; + unsigned int can_generate_field_modification_events : 1; + unsigned int can_generate_field_access_events : 1; + unsigned int can_get_bytecodes : 1; + unsigned int can_get_synthetic_attribute : 1; + unsigned int can_get_owned_monitor_info : 1; + unsigned int can_get_current_contended_monitor : 1; + unsigned int can_get_monitor_info : 1; + unsigned int can_pop_frame : 1; + unsigned int can_redefine_classes : 1; + unsigned int can_signal_thread : 1; + unsigned int can_get_source_file_name : 1; + unsigned int can_get_line_numbers : 1; + unsigned int can_get_source_debug_extension : 1; + unsigned int can_access_local_variables : 1; + unsigned int can_maintain_original_method_order : 1; + unsigned int can_generate_single_step_events : 1; + unsigned int can_generate_exception_events : 1; + unsigned int can_generate_frame_pop_events : 1; + unsigned int can_generate_breakpoint_events : 1; + unsigned int can_suspend : 1; + unsigned int can_redefine_any_class : 1; + unsigned int can_get_current_thread_cpu_time : 1; + unsigned int can_get_thread_cpu_time : 1; + unsigned int can_generate_method_entry_events : 1; + unsigned int can_generate_method_exit_events : 1; + unsigned int can_generate_all_class_hook_events : 1; + unsigned int can_generate_compiled_method_load_events : 1; + unsigned int can_generate_monitor_events : 1; + unsigned int can_generate_vm_object_alloc_events : 1; + unsigned int can_generate_native_method_bind_events : 1; + unsigned int can_generate_garbage_collection_events : 1; + unsigned int can_generate_object_free_events : 1; + unsigned int can_force_early_return : 1; + unsigned int can_get_owned_monitor_stack_depth_info : 1; + unsigned int can_get_constant_pool : 1; + unsigned int can_set_native_method_prefix : 1; + unsigned int can_retransform_classes : 1; + unsigned int can_retransform_any_class : 1; + unsigned int can_generate_resource_exhaustion_heap_events : 1; + unsigned int can_generate_resource_exhaustion_threads_events : 1; + unsigned int : 7; + unsigned int : 16; + unsigned int : 16; + unsigned int : 16; + unsigned int : 16; + unsigned int : 16; +} jvmtiCapabilities; diff --git a/tests/quickchecking/Cargo.toml b/tests/quickchecking/Cargo.toml index 2f5b3b71..eb5cdfcf 100644 --- a/tests/quickchecking/Cargo.toml +++ b/tests/quickchecking/Cargo.toml @@ -2,9 +2,19 @@ name = "quickchecking" description = "Bindgen property tests with quickcheck. Generate random valid C code and pass it to the csmith/predicate.py script" version = "0.1.0" -authors = ["Shea Newton <snewton@polysync.io>"] +authors = ["Shea Newton <sheanewt@gmail.com>"] + +[lib] +name = "quickchecking" +path = "src/lib.rs" + +[[bin]] +name = "quickchecking" +path = "src/bin.rs" [dependencies] +clap = "2.28" +lazy_static = "1.0" quickcheck = "0.4" -tempdir = "0.3" rand = "0.3" +tempdir = "0.3" diff --git a/tests/quickchecking/src/bin.rs b/tests/quickchecking/src/bin.rs new file mode 100644 index 00000000..9cf313cd --- /dev/null +++ b/tests/quickchecking/src/bin.rs @@ -0,0 +1,110 @@ +//! An application to run property tests for `bindgen` with _fuzzed_ C headers +//! using `quickcheck` +//! +//! ## Usage +//! +//! Print help +//! ```bash +//! $ cargo run --bin=quickchecking -- -h +//! ``` +//! +//! Run with default values +//! ```bash +//! $ cargo run --bin=quickchecking +//! ``` +//! +#![deny(missing_docs)] +extern crate clap; +extern crate quickchecking; + +use clap::{App, Arg}; +use std::path::Path; + +// Validate CLI argument input for generation range. +fn validate_generate_range(v: String) -> Result<(), String> { + match v.parse::<usize>() { + Ok(_) => Ok(()), + Err(_) => Err(String::from( + "Generate range could not be converted to a usize.", + )), + } +} + +// Validate CLI argument input for tests count. +fn validate_tests_count(v: String) -> Result<(), String> { + match v.parse::<usize>() { + Ok(_) => Ok(()), + Err(_) => Err(String::from( + "Tests count could not be converted to a usize.", + )), + } +} + +// Validate CLI argument input for fuzzed headers output path. +fn validate_path(v: String) -> Result<(), String> { + match Path::new(&v).is_dir() { + true => Ok(()), + false => Err(String::from("Provided directory path does not exist.")), + } +} + +fn main() { + let matches = App::new("quickchecking") + .version("0.2.0") + .about( + "Bindgen property tests with quickcheck. \ + Generate random valid C code and pass it to the \ + csmith/predicate.py script", + ) + .arg( + Arg::with_name("path") + .short("p") + .long("path") + .value_name("PATH") + .help( + "Optional. Preserve generated headers for inspection, \ + provide directory path for header output. [default: None] ", + ) + .takes_value(true) + .validator(validate_path), + ) + .arg( + Arg::with_name("range") + .short("r") + .long("range") + .value_name("RANGE") + .help( + "Sets the range quickcheck uses during generation. \ + Corresponds to things like arbitrary usize and \ + arbitrary vector length. This number doesn't have \ + to grow much for that execution time to increase \ + significantly.", + ) + .takes_value(true) + .default_value("32") + .validator(validate_generate_range), + ) + .arg( + Arg::with_name("count") + .short("c") + .long("count") + .value_name("COUNT") + .help( + "Count / number of tests to run. Running a fuzzed \ + header through the predicate.py script can take a \ + long time, especially if the generation range is \ + large. Increase this number if you're willing to \ + wait a while.", + ) + .takes_value(true) + .default_value("2") + .validator(validate_tests_count), + ) + .get_matches(); + + let output_path: Option<&str> = matches.value_of("path"); + let generate_range: usize = matches.value_of("range").unwrap().parse::<usize>().unwrap(); + let tests: usize = matches.value_of("count").unwrap().parse::<usize>().unwrap(); + + quickchecking::test_bindgen(generate_range, tests, output_path) +} diff --git a/tests/quickchecking/src/lib.rs b/tests/quickchecking/src/lib.rs index 3bea8a8e..d8633dfb 100644 --- a/tests/quickchecking/src/lib.rs +++ b/tests/quickchecking/src/lib.rs @@ -20,9 +20,107 @@ //! ``` //! #![deny(missing_docs)] +#[macro_use] +extern crate lazy_static; extern crate quickcheck; extern crate rand; extern crate tempdir; +use std::sync::Mutex; +use quickcheck::{QuickCheck, StdGen, TestResult}; +use std::fs::File; +use std::io::Write; +use tempdir::TempDir; +use std::process::{Command, Output}; +use std::path::PathBuf; +use std::error::Error; +use rand::thread_rng; + /// Contains definitions of and impls for types used to fuzz C declarations. pub mod fuzzers; + +// Global singleton, manages context across tests. For now that context is +// only the output_path for inspecting fuzzed headers (if specified). +struct Context { + output_path: Option<String>, +} + +// Initialize global context. +lazy_static! { + static ref CONTEXT: Mutex<Context> = Mutex::new(Context { output_path: None }); +} + +// Passes fuzzed header to the `csmith-fuzzing/predicate.py` script, returns +// output of the associated command. +fn run_predicate_script(header: fuzzers::HeaderC) -> Result<Output, Box<Error>> { + let dir = TempDir::new("bindgen_prop")?; + let header_path = dir.path().join("prop_test.h"); + + let mut header_file = File::create(&header_path)?; + header_file.write_all(header.to_string().as_bytes())?; + header_file.sync_all()?; + + let header_path_string; + match header_path.into_os_string().into_string() { + Ok(s) => header_path_string = s, + Err(_) => return Err(From::from("error converting path into String")), + } + + let mut predicate_script_path = PathBuf::from(env!("CARGO_MANIFEST_DIR")); + predicate_script_path.push("../../csmith-fuzzing/predicate.py"); + + let predicate_script_path_string; + match predicate_script_path.into_os_string().into_string() { + Ok(s) => predicate_script_path_string = s, + Err(_) => return Err(From::from("error converting path into String")), + } + + // Copy generated temp files to output_path directory for inspection. + // If `None`, output path not specified, don't copy. + match CONTEXT.lock().unwrap().output_path { + Some(ref path) => { + Command::new("cp") + .arg("-a") + .arg(&dir.path().to_str().unwrap()) + .arg(&path) + .output()?; + } + None => {} + } + + Ok(Command::new(&predicate_script_path_string) + .arg(&header_path_string) + .output()?) +} + +// Generatable property. Pass generated headers off to run through the +// `csmith-fuzzing/predicate.py` script. Success is measured by the success +// status of that command. +fn bindgen_prop(header: fuzzers::HeaderC) -> TestResult { + match run_predicate_script(header) { + Ok(o) => return TestResult::from_bool(o.status.success()), + Err(e) => { + println!("{:?}", e); + return TestResult::from_bool(false); + } + } +} + +/// Instantiate a Quickcheck object and use it to run property tests using +/// fuzzed C headers generated with types defined in the `fuzzers` module. +/// Success/Failure is dictated by the result of passing the fuzzed headers +/// to the `csmith-fuzzing/predicate.py` script. +pub fn test_bindgen(generate_range: usize, tests: usize, output_path: Option<&str>) { + match output_path { + Some(path) => { + CONTEXT.lock().unwrap().output_path = + Some(String::from(PathBuf::from(path).to_str().unwrap())); + } + None => {} // Path not specified, don't provide output. + } + + QuickCheck::new() + .tests(tests) + .gen(StdGen::new(thread_rng(), generate_range)) + .quickcheck(bindgen_prop as fn(fuzzers::HeaderC) -> TestResult) +} diff --git a/tests/quickchecking/tests/fuzzed-c-headers.rs b/tests/quickchecking/tests/fuzzed-c-headers.rs index f550cf0c..6b58d24b 100644 --- a/tests/quickchecking/tests/fuzzed-c-headers.rs +++ b/tests/quickchecking/tests/fuzzed-c-headers.rs @@ -1,78 +1,95 @@ + extern crate quickcheck; extern crate quickchecking; extern crate rand; -extern crate tempdir; - -use quickchecking::fuzzers; -use quickcheck::{QuickCheck, StdGen, TestResult}; -use std::fs::File; -use std::io::Write; -use tempdir::TempDir; -use std::process::{Command, Output}; -use std::path::PathBuf; -use std::error::Error; + +use quickchecking::fuzzers::{ArrayDimensionC, BaseTypeC, BasicTypeDeclarationC, DeclarationC, + DeclarationListC, FunctionPointerDeclarationC, FunctionPrototypeC, + HeaderC, ParameterC, ParameterListC, PointerLevelC, + StructDeclarationC, TypeQualifierC, UnionDeclarationC}; +use quickcheck::{Arbitrary, StdGen}; use rand::thread_rng; -fn run_predicate_script(header: fuzzers::HeaderC, header_name: &str) -> Result<Output, Box<Error>> { - let dir = TempDir::new("bindgen_prop")?; - let header_path = dir.path().join(header_name); - - let mut header_file = File::create(&header_path)?; - header_file.write_all(header.to_string().as_bytes())?; - header_file.sync_all()?; - - let header_path_string; - match header_path.into_os_string().into_string() { - Ok(s) => header_path_string = s, - Err(_) => return Err(From::from("error converting path into String")), - } - - let mut predicate_script_path = PathBuf::from(env!("CARGO_MANIFEST_DIR")); - predicate_script_path.push("../../csmith-fuzzing/predicate.py"); - - let predicate_script_path_string; - match predicate_script_path.into_os_string().into_string() { - Ok(s) => predicate_script_path_string = s, - Err(_) => return Err(From::from("error converting path into String")), - } - - // Copy generated temp files to test directory for inspection. - // Preserved for anyone interested in validating the behavior. - - let mut debug_output_path = PathBuf::from(env!("CARGO_MANIFEST_DIR")); - debug_output_path.push("tests"); - Command::new("cp") - .arg("-a") - .arg(&dir.path().to_str().unwrap()) - .arg(&debug_output_path.to_str().unwrap()) - .output()?; - - Ok(Command::new(&predicate_script_path_string) - .arg(&header_path_string) - .output()?) +#[test] +fn test_declaraion_c_does_not_panic() { + let ref mut gen = StdGen::new(thread_rng(), 50); + let _: DeclarationC = Arbitrary::arbitrary(gen); +} + +#[test] +fn test_declaraion_list_c_does_not_panic() { + let ref mut gen = StdGen::new(thread_rng(), 50); + let _: DeclarationListC = Arbitrary::arbitrary(gen); } -fn bindgen_prop(header: fuzzers::HeaderC) -> TestResult { - match run_predicate_script(header, "prop_test.h") { - Ok(o) => return TestResult::from_bool(o.status.success()), - Err(e) => { - println!("{:?}", e); - return TestResult::from_bool(false); - } - } +#[test] +fn test_base_type_c_does_not_panic() { + let ref mut gen = StdGen::new(thread_rng(), 50); + let _: BaseTypeC = Arbitrary::arbitrary(gen); +} + +#[test] +fn test_type_qualifier_c_does_not_panic() { + let ref mut gen = StdGen::new(thread_rng(), 50); + let _: TypeQualifierC = Arbitrary::arbitrary(gen); +} + +#[test] +fn test_pointer_level_c_does_not_panic() { + let ref mut gen = StdGen::new(thread_rng(), 50); + let _: PointerLevelC = Arbitrary::arbitrary(gen); +} + +#[test] +fn test_array_dimension_c_does_not_panic() { + let ref mut gen = StdGen::new(thread_rng(), 50); + let _: ArrayDimensionC = Arbitrary::arbitrary(gen); +} + +#[test] +fn test_basic_type_declaration_c_does_not_panic() { + let ref mut gen = StdGen::new(thread_rng(), 50); + let _: BasicTypeDeclarationC = Arbitrary::arbitrary(gen); +} + +#[test] +fn test_struct_declaration_c_does_not_panic() { + let ref mut gen = StdGen::new(thread_rng(), 50); + let _: StructDeclarationC = Arbitrary::arbitrary(gen); +} + +#[test] +fn test_union_declaration_c_does_not_panic() { + let ref mut gen = StdGen::new(thread_rng(), 50); + let _: UnionDeclarationC = Arbitrary::arbitrary(gen); +} + +#[test] +fn test_function_pointer_declaration_c_does_not_panic() { + let ref mut gen = StdGen::new(thread_rng(), 50); + let _: FunctionPointerDeclarationC = Arbitrary::arbitrary(gen); +} + +#[test] +fn test_function_prototype_c_does_not_panic() { + let ref mut gen = StdGen::new(thread_rng(), 50); + let _: FunctionPrototypeC = Arbitrary::arbitrary(gen); +} + +#[test] +fn test_parameter_c_does_not_panic() { + let ref mut gen = StdGen::new(thread_rng(), 50); + let _: ParameterC = Arbitrary::arbitrary(gen); +} + +#[test] +fn test_parameter_list_c_does_not_panic() { + let ref mut gen = StdGen::new(thread_rng(), 50); + let _: ParameterListC = Arbitrary::arbitrary(gen); } #[test] -fn test_bindgen() { - // Enough to generate any value in the PrimitiveTypeC `base_type` list. - let generate_range: usize = 32; - QuickCheck::new() - // Generating is relatively quick (generate_range 150 takes ~5 seconds) - // but running predicate.py takes ~30 seconds per source file / test - // when the generation range is just 32. It can take a lot longer with a - // higher generate_range. Up the number of tests or generate_range if - // you're willing to wait awhile. - .tests(2) - .gen(StdGen::new(thread_rng(), generate_range)) - .quickcheck(bindgen_prop as fn(fuzzers::HeaderC) -> TestResult) +fn test_header_c_does_not_panic() { + let ref mut gen = StdGen::new(thread_rng(), 50); + let _: HeaderC = Arbitrary::arbitrary(gen); } |