@@ -28,73 +28,69 @@ macro_rules! panic_on_tskit_error {
2828}
2929
3030macro_rules! unsafe_tsk_column_access {
31- ( $i: expr, $lo: expr, $hi: expr, $array : expr) => { {
31+ ( $i: expr, $lo: expr, $hi: expr, $owner : expr, $array : ident ) => { {
3232 if $i < $lo || ( $i as $crate:: tsk_size_t) >= $hi {
3333 None
3434 } else {
35- Some ( unsafe { * $array. offset( $i as isize ) } )
35+ debug_assert!( !( $owner) . $array. is_null( ) ) ;
36+ if !$owner. $array. is_null( ) {
37+ // SAFETY: array is not null
38+ // and we did our best effort
39+ // on bounds checking
40+ Some ( unsafe { * $owner. $array. offset( $i as isize ) } )
41+ } else {
42+ None
43+ }
3644 }
3745 } } ;
38- ( $i: expr, $lo: expr, $hi: expr, $array : expr, $output_id_type: expr) => { {
46+ ( $i: expr, $lo: expr, $hi: expr, $owner : expr, $array : ident , $output_id_type: expr) => { {
3947 if $i < $lo || ( $i as $crate:: tsk_size_t) >= $hi {
4048 None
4149 } else {
42- Some ( $output_id_type( unsafe { * $array. offset( $i as isize ) } ) )
50+ debug_assert!( !( $owner) . $array. is_null( ) ) ;
51+ if !$owner. $array. is_null( ) {
52+ // SAFETY: array is not null
53+ // and we did our best effort
54+ // on bounds checking
55+ unsafe { Some ( $output_id_type( * ( $owner. $array. offset( $i as isize ) ) ) ) }
56+ } else {
57+ None
58+ }
4359 }
4460 } } ;
4561}
4662
4763macro_rules! unsafe_tsk_column_access_and_map_into {
48- ( $i: expr, $lo: expr, $hi: expr, $array : expr) => { {
49- unsafe_tsk_column_access!( $i, $lo, $hi, $array) . map( |v| v. into( ) )
64+ ( $i: expr, $lo: expr, $hi: expr, $owner : expr, $array : ident ) => { {
65+ unsafe_tsk_column_access!( $i, $lo, $hi, $owner , $ array) . map( |v| v. into( ) )
5066 } } ;
5167}
5268
5369macro_rules! unsafe_tsk_ragged_column_access {
54- ( $i: expr, $lo: expr, $hi: expr, $array : expr, $offset_array: expr , $offset_array_len: expr ) => { {
70+ ( $i: expr, $lo: expr, $hi: expr, $owner : expr, $array : ident , $ offset_array: ident , $offset_array_len: ident , $output_id_type : ty ) => { {
5571 let i = $crate:: SizeType :: try_from( $i) . ok( ) ?;
5672 if $i < $lo || i >= $hi {
5773 None
58- } else if $offset_array_len == 0 {
74+ } else if $owner . $ offset_array_len == 0 {
5975 None
6076 } else {
61- let start = unsafe { * $offset_array. offset( $i as isize ) } ;
62- let stop = if i < $hi {
63- unsafe { * $offset_array. offset( ( $i + 1 ) as isize ) }
64- } else {
65- $offset_array_len as tsk_size_t
66- } ;
67- if start == stop {
68- None
69- } else {
70- let mut buffer = vec![ ] ;
71- for i in start..stop {
72- buffer. push( unsafe { * $array. offset( i as isize ) } ) ;
73- }
74- Some ( buffer)
77+ debug_assert!( !$owner. $array. is_null( ) ) ;
78+ if $owner. $array. is_null( ) {
79+ return None ;
7580 }
76- }
77- } } ;
78-
79- ( $i: expr, $lo: expr, $hi: expr, $array: expr, $offset_array: expr, $offset_array_len: expr, $output_id_type: ty) => { {
80- let i = $crate:: SizeType :: try_from( $i) . ok( ) ?;
81- if $i < $lo || i >= $hi {
82- None
83- } else if $offset_array_len == 0 {
84- None
85- } else {
86- let start = unsafe { * $offset_array. offset( $i as isize ) } ;
81+ // SAFETY: we have checked bounds and ensured not null
82+ let start = unsafe { * $owner. $offset_array. offset( $i as isize ) } ;
8783 let stop = if i < $hi {
88- unsafe { * $offset_array. offset( ( $i + 1 ) as isize ) }
84+ unsafe { * $owner . $ offset_array. offset( ( $i + 1 ) as isize ) }
8985 } else {
90- $offset_array_len as tsk_size_t
86+ $owner . $ offset_array_len as tsk_size_t
9187 } ;
9288 if start == stop {
9389 None
9490 } else {
9591 Some ( unsafe {
9692 std:: slice:: from_raw_parts(
97- $array. offset( start as isize ) as * const $output_id_type,
93+ $owner . $ array. offset( start as isize ) as * const $output_id_type,
9894 stop as usize - start as usize ,
9995 )
10096 } )
@@ -107,25 +103,27 @@ macro_rules! unsafe_tsk_ragged_column_access {
107103// to pass clippy checks
108104#[ allow( unused_macros) ]
109105macro_rules! unsafe_tsk_ragged_char_column_access {
110- ( $i: expr, $lo: expr, $hi: expr, $array : expr, $offset_array: expr , $offset_array_len: expr ) => { {
106+ ( $i: expr, $lo: expr, $hi: expr, $owner : expr, $array : ident , $ offset_array: ident , $offset_array_len: ident ) => { {
111107 let i = $crate:: SizeType :: try_from( $i) ?;
112108 if $i < $lo || i >= $hi {
113109 Err ( TskitError :: IndexError { } )
114- } else if $offset_array_len == 0 {
110+ } else if $owner . $ offset_array_len == 0 {
115111 Ok ( None )
116112 } else {
117- let start = unsafe { * $offset_array. offset( $i as isize ) } ;
113+ assert!( !$owner. $array. is_null( ) ) ;
114+ assert!( !$owner. $offset_array. is_null( ) ) ;
115+ let start = unsafe { * $owner. $offset_array. offset( $i as isize ) } ;
118116 let stop = if i < $hi {
119- unsafe { * $offset_array. offset( ( $i + 1 ) as isize ) }
117+ unsafe { * $owner . $ offset_array. offset( ( $i + 1 ) as isize ) }
120118 } else {
121- $offset_array_len as tsk_size_t
119+ $owner . $ offset_array_len as tsk_size_t
122120 } ;
123121 if start == stop {
124122 Ok ( None )
125123 } else {
126124 let mut buffer = String :: new( ) ;
127125 for i in start..stop {
128- buffer. push( unsafe { * $array. offset( i as isize ) as u8 as char } ) ;
126+ buffer. push( unsafe { * $owner . $ array. offset( i as isize ) as u8 as char } ) ;
129127 }
130128 Ok ( Some ( buffer) )
131129 }
0 commit comments