diff --git a/include/servicepoint.h b/include/servicepoint.h index 9edeaf9..51b00ca 100644 --- a/include/servicepoint.h +++ b/include/servicepoint.h @@ -388,6 +388,15 @@ void sp_bitmap_fill(Bitmap */*notnull*/ bitmap, bool value); */ void sp_bitmap_free(Bitmap */*notnull*/ bitmap); +/** + * Tries to convert the BitVec to a Bitmap. + * + * The provided BitVec gets consumed. + * + * Returns NULL in case of error. + */ +Bitmap *sp_bitmap_from_bitvec(size_t width, SPBitVec */*notnull*/ bitvec); + /** * Gets the current value at the specified position in the [Bitmap]. * @@ -411,6 +420,11 @@ bool sp_bitmap_get(Bitmap */*notnull*/ bitmap, size_t x, size_t y); */ size_t sp_bitmap_height(Bitmap */*notnull*/ bitmap); +/** + * Consumes the Bitmap and returns the contained BitVec + */ +SPBitVec */*notnull*/ sp_bitmap_into_bitvec(Bitmap */*notnull*/ bitmap); + /** * Loads a [Bitmap] with the specified dimensions from the provided data. * diff --git a/src/bitmap.rs b/src/bitmap.rs index c166881..f203395 100644 --- a/src/bitmap.rs +++ b/src/bitmap.rs @@ -1,5 +1,5 @@ use crate::byte_slice::ByteSlice; -use crate::{heap_drop, heap_move, heap_move_nonnull}; +use crate::{heap_drop, heap_move, heap_move_nonnull, SPBitVec}; use servicepoint::{Bitmap, DataRef, Grid}; use std::ptr::NonNull; @@ -68,6 +68,24 @@ pub unsafe extern "C" fn sp_bitmap_load( } } +/// Tries to convert the BitVec to a Bitmap. +/// +/// The provided BitVec gets consumed. +/// +/// Returns NULL in case of error. +#[no_mangle] +pub unsafe extern "C" fn sp_bitmap_from_bitvec( + width: usize, + bitvec: NonNull, +) -> *mut Bitmap { + let bitvec = unsafe { *Box::from_raw(bitvec.as_ptr()) }; + if let Ok(bitmap) = Bitmap::from_bitvec(width, bitvec.0) { + heap_move(bitmap) + } else { + std::ptr::null_mut() + } +} + /// Clones a [Bitmap]. #[no_mangle] pub unsafe extern "C" fn sp_bitmap_clone( @@ -172,3 +190,12 @@ pub unsafe extern "C" fn sp_bitmap_unsafe_data_ref( ) -> ByteSlice { unsafe { ByteSlice::from_slice(bitmap.as_mut().data_ref_mut()) } } + +/// Consumes the Bitmap and returns the contained BitVec +#[no_mangle] +pub unsafe extern "C" fn sp_bitmap_into_bitvec( + bitmap: NonNull, +) -> NonNull { + let bitmap = unsafe { *Box::from_raw(bitmap.as_ptr()) }; + heap_move_nonnull(SPBitVec(bitmap.into())) +}