@@ -1288,6 +1288,27 @@ mod tests {
12881288 ( c"=d" , Float { bytes : 8 } ) ,
12891289 ( c"=z" , Unknown ) ,
12901290 ( c"=0" , Unknown ) ,
1291+ // bare char (no prefix) goes to native_element_type_from_type_char
1292+ (
1293+ c"b" ,
1294+ SignedInteger {
1295+ bytes : size_of :: < c_schar > ( ) ,
1296+ } ,
1297+ ) ,
1298+ (
1299+ c"B" ,
1300+ UnsignedInteger {
1301+ bytes : size_of :: < c_uchar > ( ) ,
1302+ } ,
1303+ ) ,
1304+ ( c"?" , Bool ) ,
1305+ ( c"f" , Float { bytes : 4 } ) ,
1306+ ( c"d" , Float { bytes : 8 } ) ,
1307+ ( c"z" , Unknown ) ,
1308+ // <, >, ! prefixes go to standard_element_type_from_type_char
1309+ ( c"<i" , SignedInteger { bytes : 4 } ) ,
1310+ ( c">H" , UnsignedInteger { bytes : 2 } ) ,
1311+ ( c"!q" , SignedInteger { bytes : 8 } ) ,
12911312 // unknown prefix -> Unknown
12921313 ( c":b" , Unknown ) ,
12931314 ] {
@@ -1325,6 +1346,7 @@ mod tests {
13251346 assert_eq ! ( slice. len( ) , 5 ) ;
13261347 assert_eq ! ( slice[ 0 ] . get( ) , b'a' ) ;
13271348 assert_eq ! ( slice[ 2 ] . get( ) , b'c' ) ;
1349+ assert_eq ! ( unsafe { * slice[ 0 ] . as_ptr( ) } , b'a' ) ;
13281350
13291351 assert_eq ! ( unsafe { * ( buffer. get_ptr( & [ 1 ] ) . cast:: <u8 >( ) ) } , b'b' ) ;
13301352
@@ -1398,24 +1420,6 @@ mod tests {
13981420 } ) ;
13991421 }
14001422
1401- #[ test]
1402- fn test_untyped_buffer ( ) {
1403- Python :: attach ( |py| {
1404- let bytes = PyBytes :: new ( py, b"abcde" ) ;
1405- let untyped = PyUntypedBuffer :: get ( & bytes) . unwrap ( ) ;
1406- assert_eq ! ( untyped. dimensions( ) , 1 ) ;
1407- assert_eq ! ( untyped. item_count( ) , 5 ) ;
1408- assert_eq ! ( untyped. format( ) . to_str( ) . unwrap( ) , "B" ) ;
1409- assert_eq ! ( untyped. shape( ) , [ 5 ] ) ;
1410-
1411- let typed: & PyBuffer < u8 > = untyped. as_typed ( ) . unwrap ( ) ;
1412- assert_eq ! ( typed. dimensions( ) , 1 ) ;
1413- assert_eq ! ( typed. item_count( ) , 5 ) ;
1414- assert_eq ! ( typed. format( ) . to_str( ) . unwrap( ) , "B" ) ;
1415- assert_eq ! ( typed. shape( ) , [ 5 ] ) ;
1416- } ) ;
1417- }
1418-
14191423 #[ test]
14201424 fn test_obj_getter ( ) {
14211425 Python :: attach ( |py| {
@@ -1439,6 +1443,67 @@ mod tests {
14391443 } ) ;
14401444 }
14411445
1446+ #[ test]
1447+ fn test_copy_to_fortran_slice ( ) {
1448+ Python :: attach ( |py| {
1449+ let array = py
1450+ . import ( "array" )
1451+ . unwrap ( )
1452+ . call_method ( "array" , ( "f" , ( 1.0 , 1.5 , 2.0 , 2.5 ) ) , None )
1453+ . unwrap ( ) ;
1454+ let buffer = PyBuffer :: get ( & array) . unwrap ( ) ;
1455+
1456+ // wrong length
1457+ assert ! ( buffer. copy_to_fortran_slice( py, & mut [ 0.0f32 ] ) . is_err( ) ) ;
1458+ // correct length
1459+ let mut arr = [ 0.0f32 ; 4 ] ;
1460+ buffer. copy_to_fortran_slice ( py, & mut arr) . unwrap ( ) ;
1461+ assert_eq ! ( arr, [ 1.0 , 1.5 , 2.0 , 2.5 ] ) ;
1462+ } ) ;
1463+ }
1464+
1465+ #[ test]
1466+ fn test_copy_from_slice_wrong_length ( ) {
1467+ Python :: attach ( |py| {
1468+ let array = py
1469+ . import ( "array" )
1470+ . unwrap ( )
1471+ . call_method ( "array" , ( "f" , ( 1.0 , 1.5 , 2.0 , 2.5 ) ) , None )
1472+ . unwrap ( ) ;
1473+ let buffer = PyBuffer :: get ( & array) . unwrap ( ) ;
1474+ // writable buffer, but wrong length
1475+ assert ! ( !buffer. readonly( ) ) ;
1476+ assert ! ( buffer. copy_from_slice( py, & [ 0.0f32 ; 2 ] ) . is_err( ) ) ;
1477+ assert ! ( buffer. copy_from_fortran_slice( py, & [ 0.0f32 ; 2 ] ) . is_err( ) ) ;
1478+ } ) ;
1479+ }
1480+
1481+ #[ test]
1482+ fn test_untyped_buffer ( ) {
1483+ Python :: attach ( |py| {
1484+ let bytes = PyBytes :: new ( py, b"abcde" ) ;
1485+ let buffer = PyUntypedBuffer :: get ( & bytes) . unwrap ( ) ;
1486+ assert_eq ! ( buffer. dimensions( ) , 1 ) ;
1487+ assert_eq ! ( buffer. item_count( ) , 5 ) ;
1488+ assert_eq ! ( buffer. format( ) . to_str( ) . unwrap( ) , "B" ) ;
1489+ assert_eq ! ( buffer. shape( ) , [ 5 ] ) ;
1490+ assert ! ( !buffer. buf_ptr( ) . is_null( ) ) ;
1491+ assert_eq ! ( buffer. strides( ) , & [ 1 ] ) ;
1492+ assert_eq ! ( buffer. len_bytes( ) , 5 ) ;
1493+ assert_eq ! ( buffer. item_size( ) , 1 ) ;
1494+ assert ! ( buffer. readonly( ) ) ;
1495+ assert ! ( buffer. suboffsets( ) . is_none( ) ) ;
1496+
1497+ assert ! ( format!( "{:?}" , buffer) . starts_with( "PyUntypedBuffer { buf: " ) ) ;
1498+
1499+ let typed: & PyBuffer < u8 > = buffer. as_typed ( ) . unwrap ( ) ;
1500+ assert_eq ! ( typed. dimensions( ) , 1 ) ;
1501+ assert_eq ! ( typed. item_count( ) , 5 ) ;
1502+ assert_eq ! ( typed. format( ) . to_str( ) . unwrap( ) , "B" ) ;
1503+ assert_eq ! ( typed. shape( ) , [ 5 ] ) ;
1504+ } ) ;
1505+ }
1506+
14421507 #[ test]
14431508 fn test_untyped_buffer_view ( ) {
14441509 Python :: attach ( |py| {
@@ -1536,6 +1601,48 @@ mod tests {
15361601 } ) ;
15371602 }
15381603
1604+ #[ test]
1605+ fn test_typed_buffer_view_with_flags ( ) {
1606+ Python :: attach ( |py| {
1607+ let array = py
1608+ . import ( "array" )
1609+ . unwrap ( )
1610+ . call_method ( "array" , ( "f" , ( 1.0 , 1.5 , 2.0 , 2.5 ) ) , None )
1611+ . unwrap ( ) ;
1612+
1613+ PyBufferView :: < f32 , Known , Unknown , Unknown > :: with_flags (
1614+ & array,
1615+ ffi:: PyBUF_ND ,
1616+ |view| {
1617+ assert_eq ! ( view. item_count( ) , 4 ) ;
1618+ assert_eq ! ( view. format( ) . to_str( ) . unwrap( ) , "f" ) ;
1619+
1620+ let slice = view. as_slice ( py) . unwrap ( ) ;
1621+ assert_eq ! ( slice[ 0 ] . get( ) , 1.0 ) ;
1622+ assert_eq ! ( slice[ 3 ] . get( ) , 2.5 ) ;
1623+
1624+ let mut_slice = view. as_mut_slice ( py) . unwrap ( ) ;
1625+ mut_slice[ 0 ] . set ( 9.0 ) ;
1626+ assert_eq ! ( slice[ 0 ] . get( ) , 9.0 ) ;
1627+ } ,
1628+ )
1629+ . unwrap ( ) ;
1630+ } ) ;
1631+ }
1632+
1633+ #[ test]
1634+ fn test_typed_buffer_view_with_flags_incompatible ( ) {
1635+ Python :: attach ( |py| {
1636+ let bytes = PyBytes :: new ( py, b"abcde" ) ;
1637+ let result = PyBufferView :: < f32 , Known , Unknown , Unknown > :: with_flags (
1638+ & bytes,
1639+ ffi:: PyBUF_ND ,
1640+ |_view| { } ,
1641+ ) ;
1642+ assert ! ( result. is_err( ) ) ;
1643+ } ) ;
1644+ }
1645+
15391646 #[ test]
15401647 fn test_buffer_view_error ( ) {
15411648 Python :: attach ( |py| {
0 commit comments