bitfields raw pointer accessors · Issue #2674 · rust-lang/rust-bindgen (original) (raw)

When creating bindings for a struct with bitfields the accessor functions that are created take an immutable receiver (&self). This is a problem if the underlying type is used by both Rust and C, since Rust is not allowed to create &self references, since the C side might modify the value at any time.
One solution could be to create raw accessor functions that allow access via *const Self.

Input C Header

struct foo { unsigned available:1; };

Bindgen Invocation

impl foo { #[inline] pub fn available(&self) -> ::std::os::raw::c_uint { unsafe { ::std::mem::transmute(self._bitfield_1.get(0usize, 1u8) as u32) } } #[inline] pub fn set_available(&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 new_bitfield_1( available: ::std::os::raw::c_uint, ) -> __BindgenBitfieldUnit<[u8; 1usize]> { let mut __bindgen_bitfield_unit: __BindgenBitfieldUnit<[u8; 1usize]> = Default::default(); __bindgen_bitfield_unit.set(0usize, 1u8, { let available: u32 = unsafe { ::std::mem::transmute(available) }; available as u64 }); __bindgen_bitfield_unit } }

Expected Results

Additional functions that should be generated:

impl foo { #[inline] pub unsafe fn raw_available(this: *const Self) -> ::std::os::raw::c_uint { unsafe { ::std::mem::transmute(__BindgenBitfieldUnit::raw_get( addr_of!((*this)._bitfield_1), 0usize, 1u8, ) as u32) } }

#[inline]
pub unsafe fn raw_set_available(this: *mut Self, val: ::std::os::raw::c_uint) {
    unsafe {
        let val: u32 = ::std::mem::transmute(val);
        __BindgenBitfieldUnit::raw_set(addr_of!((*this)._bitfield_1), 0usize, 1u8, val as u64)
    }
}

}

This also requires changes to the generated __BingenBitfieldUnit.