use std::ffi::CStr;
use uuid::Uuid;
use crate::{
devno::BlkidDevno,
err::BlkidErr,
utils::{BlkidBytes, BlkidSectors},
Result,
};
pub struct BlkidParttable(libblkid_rs_sys::blkid_parttable);
impl BlkidParttable {
pub fn get_type(&self) -> Result<String> {
Ok(unsafe {
CStr::from_ptr(errno_ptr!(libblkid_rs_sys::blkid_parttable_get_type(
self.0
))?)
}
.to_str()?
.to_string())
}
pub fn get_id(&self) -> Result<String> {
Ok(
unsafe { CStr::from_ptr(errno_ptr!(libblkid_rs_sys::blkid_parttable_get_id(self.0))?) }
.to_str()?
.to_string(),
)
}
pub fn get_offset(&self) -> Result<BlkidBytes> {
Ok(BlkidBytes::new(errno_with_ret!(unsafe {
libblkid_rs_sys::blkid_parttable_get_offset(self.0)
})?))
}
pub fn get_parent(&self) -> Option<BlkidPartition> {
option_ptr!(unsafe { libblkid_rs_sys::blkid_parttable_get_parent(self.0) })
.map(BlkidPartition)
}
}
pub struct BlkidPartition(libblkid_rs_sys::blkid_partition);
impl BlkidPartition {
pub fn get_table(&self) -> Result<BlkidParttable> {
Ok(BlkidParttable(errno_ptr!(unsafe {
libblkid_rs_sys::blkid_partition_get_table(self.0)
})?))
}
pub fn get_name(&self) -> Result<Option<String>> {
let char_ptr =
match option_ptr!(unsafe { libblkid_rs_sys::blkid_partition_get_name(self.0) }) {
Some(ptr) => ptr,
None => return Ok(None),
};
unsafe { CStr::from_ptr(char_ptr) }
.to_str()
.map(|s| Some(s.to_string()))
.map_err(BlkidErr::UTF8)
}
pub fn get_uuid(&self) -> Result<Option<Uuid>> {
let char_ptr =
match option_ptr!(unsafe { libblkid_rs_sys::blkid_partition_get_uuid(self.0) }) {
Some(ptr) => ptr,
None => return Ok(None),
};
match unsafe { CStr::from_ptr(char_ptr) }.to_str() {
Ok(s) => Ok(Some(Uuid::parse_str(s).map_err(BlkidErr::Uuid)?)),
Err(e) => Err(BlkidErr::UTF8(e)),
}
}
pub fn get_partno(&self) -> Result<libc::c_uint> {
errno_with_ret!(unsafe { libblkid_rs_sys::blkid_partition_get_partno(self.0) })
.map(|i| i as libc::c_uint)
}
pub fn get_start(&self) -> BlkidSectors {
BlkidSectors::new(unsafe { libblkid_rs_sys::blkid_partition_get_start(self.0) })
}
pub fn get_size(&self) -> BlkidSectors {
BlkidSectors::new(unsafe { libblkid_rs_sys::blkid_partition_get_size(self.0) })
}
pub fn get_type(&self) -> libc::c_int {
unsafe { libblkid_rs_sys::blkid_partition_get_type(self.0) }
}
pub fn get_type_string(&self) -> Result<String> {
Ok(unsafe {
CStr::from_ptr(errno_ptr!(
libblkid_rs_sys::blkid_partition_get_type_string(self.0)
)?)
}
.to_str()?
.to_string())
}
pub fn get_flags(&self) -> libc::c_ulonglong {
unsafe { libblkid_rs_sys::blkid_partition_get_flags(self.0) }
}
pub fn is_logical(&self) -> bool {
(unsafe { libblkid_rs_sys::blkid_partition_is_logical(self.0) }) != 0
}
pub fn is_extended(&self) -> bool {
(unsafe { libblkid_rs_sys::blkid_partition_is_extended(self.0) }) != 0
}
pub fn is_primary(&self) -> bool {
(unsafe { libblkid_rs_sys::blkid_partition_is_primary(self.0) }) != 0
}
}
pub struct BlkidPartlist(libblkid_rs_sys::blkid_partlist);
impl BlkidPartlist {
pub(crate) fn new(partlist: libblkid_rs_sys::blkid_partlist) -> BlkidPartlist {
BlkidPartlist(partlist)
}
pub fn number_of_partitions(&mut self) -> Result<libc::c_int> {
errno_with_ret!(unsafe { libblkid_rs_sys::blkid_partlist_numof_partitions(self.0) })
}
pub fn get_table(&mut self) -> Result<BlkidParttable> {
Ok(BlkidParttable(errno_ptr!(unsafe {
libblkid_rs_sys::blkid_partlist_get_table(self.0)
})?))
}
pub fn get_partition(&mut self, index: libc::c_int) -> Result<BlkidPartition> {
Ok(BlkidPartition(errno_ptr!(unsafe {
libblkid_rs_sys::blkid_partlist_get_partition(self.0, index)
})?))
}
pub fn get_partition_by_partno(&mut self, num: libc::c_int) -> Result<BlkidPartition> {
Ok(BlkidPartition(errno_ptr!(unsafe {
libblkid_rs_sys::blkid_partlist_get_partition_by_partno(self.0, num)
})?))
}
pub fn get_partition_by_devno(&mut self, dev: &BlkidDevno) -> Result<BlkidPartition> {
Ok(BlkidPartition(errno_ptr!(unsafe {
libblkid_rs_sys::blkid_partlist_devno_to_partition(self.0, dev.as_dev_t())
})?))
}
}