Skip to content

Commit 7f26d60

Browse files
authored
refactor: generalize slice building in sys (#427)
1 parent caf735d commit 7f26d60

File tree

5 files changed

+28
-43
lines changed

5 files changed

+28
-43
lines changed

src/_macros.rs

Lines changed: 2 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1016,14 +1016,7 @@ macro_rules! build_table_column_slice_getter {
10161016
($(#[$attr:meta])* => $column: ident, $name: ident, $cast: ty) => {
10171017
$(#[$attr])*
10181018
pub fn $name(&self) -> &[$cast] {
1019-
// Caveat: num_rows is u64 but we need usize
1020-
// The conversion is fallible but unlikely.
1021-
let num_rows =
1022-
usize::try_from(self.num_rows()).expect("conversion of num_rows to usize failed");
1023-
let ptr = self.as_ref().$column as *const $cast;
1024-
// SAFETY: tables are initialzed, num rows comes
1025-
// from the C back end.
1026-
unsafe { std::slice::from_raw_parts(ptr, num_rows) }
1019+
$crate::sys::generate_slice(self.as_ref().$column, self.num_rows())
10271020
}
10281021
};
10291022
}
@@ -1032,14 +1025,7 @@ macro_rules! build_table_column_slice_mut_getter {
10321025
($(#[$attr:meta])* => $column: ident, $name: ident, $cast: ty) => {
10331026
$(#[$attr])*
10341027
pub fn $name(&mut self) -> &mut [$cast] {
1035-
// Caveat: num_rows is u64 but we need usize
1036-
// The conversion is fallible but unlikely.
1037-
let num_rows =
1038-
usize::try_from(self.num_rows()).expect("conversion of num_rows to usize failed");
1039-
let ptr = self.as_ref().$column as *mut $cast;
1040-
// SAFETY: tables are initialzed, num rows comes
1041-
// from the C back end.
1042-
unsafe { std::slice::from_raw_parts_mut(ptr, num_rows) }
1028+
$crate::sys::generate_slice_mut(self.as_ref().$column, self.num_rows())
10431029
}
10441030
};
10451031
}

src/node_table.rs

Lines changed: 2 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -224,22 +224,12 @@ impl NodeTable {
224224

225225
#[deprecated(since = "0.12.0", note = "use flags_slice_mut instead")]
226226
pub fn flags_array_mut(&mut self) -> &mut [NodeFlags] {
227-
unsafe {
228-
std::slice::from_raw_parts_mut(
229-
self.as_ref().flags.cast::<NodeFlags>(),
230-
usize::try_from(self.as_ref().num_rows).unwrap_or(0),
231-
)
232-
}
227+
sys::generate_slice_mut(self.as_ref().flags, self.num_rows())
233228
}
234229

235230
#[deprecated(since = "0.12.0", note = "use time_slice_mut instead")]
236231
pub fn time_array_mut(&mut self) -> &mut [Time] {
237-
unsafe {
238-
std::slice::from_raw_parts_mut(
239-
self.as_ref().time.cast::<Time>(),
240-
usize::try_from(self.as_ref().num_rows).unwrap_or(0),
241-
)
242-
}
232+
sys::generate_slice_mut(self.as_ref().flags, self.num_rows())
243233
}
244234

245235
/// Return the ``population`` value from row ``row`` of the table.

src/sys.rs

Lines changed: 13 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -134,11 +134,20 @@ pub fn tsk_ragged_column_access<
134134
.map(|(p, n)| unsafe { std::slice::from_raw_parts(p.cast::<O>(), n) })
135135
}
136136

137-
pub fn tree_array_slice<'a, L: Into<bindings::tsk_size_t>>(
138-
data: *const bindings::tsk_id_t,
137+
pub fn generate_slice<'a, L: Into<bindings::tsk_size_t>, I, O>(
138+
data: *const I,
139139
length: L,
140-
) -> &'a [crate::NodeId] {
140+
) -> &'a [O] {
141141
assert!(!data.is_null());
142142
// SAFETY: pointer is not null, length comes from C API
143-
unsafe { std::slice::from_raw_parts(data.cast::<crate::NodeId>(), length.into() as usize) }
143+
unsafe { std::slice::from_raw_parts(data.cast::<O>(), length.into() as usize) }
144+
}
145+
146+
pub fn generate_slice_mut<'a, L: Into<bindings::tsk_size_t>, I, O>(
147+
data: *mut I,
148+
length: L,
149+
) -> &'a mut [O] {
150+
assert!(!data.is_null());
151+
// SAFETY: pointer is not null, length comes from C API
152+
unsafe { std::slice::from_raw_parts_mut(data.cast::<O>(), length.into() as usize) }
144153
}

src/tree_interface.rs

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ impl TreeInterface {
6969
/// }
7070
/// ```
7171
pub fn parent_array(&self) -> &[NodeId] {
72-
sys::tree_array_slice(self.as_ref().parent, self.array_len)
72+
sys::generate_slice(self.as_ref().parent, self.array_len)
7373
}
7474

7575
/// # Failing examples
@@ -107,7 +107,7 @@ impl TreeInterface {
107107
unsafe { ll_bindings::tsk_treeseq_get_num_samples((*self.as_ptr()).tree_sequence) };
108108
err_if_not_tracking_samples!(
109109
self.flags,
110-
sys::tree_array_slice(self.as_ref().samples, num_samples)
110+
sys::generate_slice(self.as_ref().samples, num_samples)
111111
)
112112
}
113113

@@ -144,7 +144,7 @@ impl TreeInterface {
144144
pub fn next_sample_array(&self) -> Result<&[NodeId], TskitError> {
145145
err_if_not_tracking_samples!(
146146
self.flags,
147-
sys::tree_array_slice(self.as_ref().next_sample, self.array_len)
147+
sys::generate_slice(self.as_ref().next_sample, self.array_len)
148148
)
149149
}
150150

@@ -181,7 +181,7 @@ impl TreeInterface {
181181
pub fn left_sample_array(&self) -> Result<&[NodeId], TskitError> {
182182
err_if_not_tracking_samples!(
183183
self.flags,
184-
sys::tree_array_slice(self.as_ref().left_sample, self.array_len)
184+
sys::generate_slice(self.as_ref().left_sample, self.array_len)
185185
)
186186
}
187187

@@ -218,7 +218,7 @@ impl TreeInterface {
218218
pub fn right_sample_array(&self) -> Result<&[NodeId], TskitError> {
219219
err_if_not_tracking_samples!(
220220
self.flags,
221-
sys::tree_array_slice(self.as_ref().right_sample, self.array_len)
221+
sys::generate_slice(self.as_ref().right_sample, self.array_len)
222222
)
223223
}
224224

@@ -239,7 +239,7 @@ impl TreeInterface {
239239
/// }
240240
/// ```
241241
pub fn left_sib_array(&self) -> &[NodeId] {
242-
sys::tree_array_slice(self.as_ref().left_sib, self.array_len)
242+
sys::generate_slice(self.as_ref().left_sib, self.array_len)
243243
}
244244

245245
/// # Failing examples
@@ -259,7 +259,7 @@ impl TreeInterface {
259259
/// }
260260
/// ```
261261
pub fn right_sib_array(&self) -> &[NodeId] {
262-
sys::tree_array_slice(self.as_ref().right_sib, self.array_len)
262+
sys::generate_slice(self.as_ref().right_sib, self.array_len)
263263
}
264264

265265
/// # Failing examples
@@ -279,7 +279,7 @@ impl TreeInterface {
279279
/// }
280280
/// ```
281281
pub fn left_child_array(&self) -> &[NodeId] {
282-
sys::tree_array_slice(self.as_ref().left_child, self.array_len)
282+
sys::generate_slice(self.as_ref().left_child, self.array_len)
283283
}
284284

285285
/// # Failing examples
@@ -299,7 +299,7 @@ impl TreeInterface {
299299
/// }
300300
/// ```
301301
pub fn right_child_array(&self) -> &[NodeId] {
302-
sys::tree_array_slice(self.as_ref().right_child, self.array_len)
302+
sys::generate_slice(self.as_ref().right_child, self.array_len)
303303
}
304304

305305
// error if we are not tracking samples,
@@ -405,7 +405,7 @@ impl TreeInterface {
405405
pub fn sample_nodes(&self) -> &[NodeId] {
406406
let num_samples =
407407
unsafe { ll_bindings::tsk_treeseq_get_num_samples((*self.as_ptr()).tree_sequence) };
408-
sys::tree_array_slice(self.as_ref().samples, num_samples)
408+
sys::generate_slice(self.as_ref().samples, num_samples)
409409
}
410410

411411
/// Return an [`Iterator`] from the node `u` to the root of the tree,

src/trees.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -396,7 +396,7 @@ impl TreeSequence {
396396
/// Get the list of sample nodes as a slice.
397397
pub fn sample_nodes(&self) -> &[NodeId] {
398398
let num_samples = unsafe { ll_bindings::tsk_treeseq_get_num_samples(self.as_ptr()) };
399-
sys::tree_array_slice(self.as_ref().samples, num_samples)
399+
sys::generate_slice(self.as_ref().samples, num_samples)
400400
}
401401

402402
/// Get the number of trees.

0 commit comments

Comments
 (0)