Skip to content

Commit 5ff3614

Browse files
committed
Fix some clippy warnings
1 parent 6db24bb commit 5ff3614

3 files changed

Lines changed: 60 additions & 57 deletions

File tree

src/lib.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@
2222
2323

2424
#![allow(clippy::needless_return, clippy::redundant_field_names)]
25+
#![forbid(clippy::as_ptr_cast_mut, clippy::ptr_cast_constness)]
2526

2627
use std::{ffi::c_void, ptr::NonNull};
2728

@@ -350,7 +351,7 @@ impl DLPackTensor {
350351
/// Consumes the `DLPackTensor`, returning the underlying raw pointer.
351352
///
352353
/// # Safety
353-
///
354+
///
354355
/// The caller is responsible for managing the memory and calling the deleter
355356
/// when the tensor is no longer needed.
356357
pub fn into_raw(self) -> NonNull<sys::DLManagedTensorVersioned>{

src/ndarray.rs

Lines changed: 17 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,6 @@
3838
//! let tensor_ref: DLPackTensorRef = (&array).try_into().unwrap();
3939
//! ```
4040
41-
use std::ffi::c_void;
4241
use ndarray::{Array, ArcArray, Dimension, ShapeBuilder};
4342

4443
use crate::data_types::{CastError, DLPackPointerCast, GetDLPackDataType};
@@ -376,7 +375,7 @@ struct ManagerContext<T> {
376375

377376
unsafe extern "C" fn deleter_fn<T>(manager: *mut sys::DLManagedTensorVersioned) {
378377
// Reconstruct the box and drop it, freeing the memory.
379-
let ctx = (*manager).manager_ctx as *mut ManagerContext<T>;
378+
let ctx = (*manager).manager_ctx.cast::<ManagerContext<T>>();
380379
let _ = Box::from_raw(ctx);
381380
}
382381

@@ -398,7 +397,11 @@ where
398397
});
399398

400399
let dl_tensor = sys::DLTensor {
401-
data: ctx._array.as_ptr() as *mut _,
400+
// Casting to a mut pointer is not necessarily safe, but is required
401+
// by DLPack. The data can be mutated through this pointer, we
402+
// should try to find a way to make this work in Rust type system in
403+
// the future.
404+
data: ctx._array.as_ptr().cast_mut().cast(),
402405
device: sys::DLDevice {
403406
device_type: sys::DLDeviceType::kDLCPU,
404407
device_id: 0,
@@ -412,7 +415,7 @@ where
412415

413416
let managed_tensor = sys::DLManagedTensorVersioned {
414417
version: sys::DLPackVersion::current(),
415-
manager_ctx: Box::into_raw(ctx) as *mut _,
418+
manager_ctx: Box::into_raw(ctx).cast(),
416419
deleter: Some(deleter_fn::<Array<T, D>>),
417420
flags: 0,
418421
dl_tensor,
@@ -446,26 +449,24 @@ where
446449
strides,
447450
});
448451

449-
let data_ptr = ctx._array.as_ptr() as *mut c_void;
450-
let shape_ptr = ctx.shape.as_mut_ptr();
451-
let strides_ptr = ctx.strides.as_mut_ptr();
452452

453453
let dl_tensor = sys::DLTensor {
454-
data: data_ptr,
454+
// Same as above, casting to a mut pointer is not necessarily safe.
455+
data: ctx._array.as_ptr().cast_mut().cast(),
455456
device: sys::DLDevice {
456457
device_type: sys::DLDeviceType::kDLCPU,
457458
device_id: 0,
458459
},
459460
ndim,
460461
dtype: T::get_dlpack_data_type(),
461-
shape: shape_ptr,
462-
strides: strides_ptr,
462+
shape: ctx.shape.as_mut_ptr(),
463+
strides: ctx.strides.as_mut_ptr(),
463464
byte_offset: 0,
464465
};
465466

466467
let managed_tensor = sys::DLManagedTensorVersioned {
467468
version: sys::DLPackVersion::current(),
468-
manager_ctx: Box::into_raw(ctx) as *mut _,
469+
manager_ctx: Box::into_raw(ctx).cast(),
469470
deleter: Some(deleter_fn::<ArcArray<T, D>>),
470471
flags: 0,
471472
dl_tensor,
@@ -486,12 +487,12 @@ mod tests {
486487

487488
#[test]
488489
fn test_dlpack_to_ndarray() {
489-
let mut data = vec![1.0f32, 2.0, 3.0, 4.0, 5.0, 6.0];
490+
let data = [1.0f32, 2.0, 3.0, 4.0, 5.0, 6.0];
490491
let mut shape = vec![2i64, 3];
491492
let mut strides = vec![3i64, 1];
492493

493494
let dl_tensor = DLTensor {
494-
data: data.as_mut_ptr() as *mut _,
495+
data: data.as_ptr().cast_mut().cast(),
495496
device: DLDevice {
496497
device_type: DLDeviceType::kDLCPU,
497498
device_id: 0,
@@ -518,7 +519,7 @@ mod tests {
518519
let mut strides = vec![1i64, 2];
519520

520521
let dl_tensor = DLTensor {
521-
data: data.as_mut_ptr() as *mut _,
522+
data: data.as_mut_ptr().cast(),
522523
device: DLDevice {
523524
device_type: DLDeviceType::kDLCPU,
524525
device_id: 0,
@@ -544,7 +545,7 @@ mod tests {
544545
let mut shape = vec![1i64];
545546

546547
let dl_tensor = DLTensor {
547-
data: data.as_mut_ptr() as *mut _,
548+
data: data.as_mut_ptr().cast(),
548549
device: DLDevice {
549550
device_type: DLDeviceType::kDLCUDA,
550551
device_id: 0,
@@ -587,7 +588,7 @@ mod tests {
587588
let mut strides = vec![3i64, 1];
588589

589590
let dl_tensor = DLTensor {
590-
data: data.as_mut_ptr() as *mut _,
591+
data: data.as_mut_ptr().cast(),
591592
device: DLDevice {
592593
device_type: DLDeviceType::kDLCPU,
593594
device_id: 0,

src/sys.rs

Lines changed: 41 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -373,7 +373,7 @@ pub struct DLManagedTensorVersioned {
373373
///----------------------------------------------------------------------
374374
/// DLPack `__dlpack_c_exchange_api__` fast exchange protocol definitions
375375
///----------------------------------------------------------------------
376-
376+
///
377377
/// Request a producer library to create a new tensor.
378378
///
379379
/// Create a new `DLManagedTensorVersioned` within the context of the producer
@@ -384,17 +384,17 @@ pub struct DLManagedTensorVersioned {
384384
/// # Arguments
385385
///
386386
/// * `prototype` - The prototype DLTensor. Only the dtype, ndim, shape,
387-
/// and device fields are used.
387+
/// and device fields are used.
388388
/// * `out` - The output DLManagedTensorVersioned.
389389
/// * `error_ctx` - Context for `SetError`.
390390
/// * `SetError` - The function to set the error.
391391
///
392392
/// # Returns
393-
///
393+
///
394394
/// The owning DLManagedTensorVersioned* or NULL on failure.
395395
/// SetError is called exactly when NULL is returned (the implementer
396396
/// must ensure this).
397-
///
397+
///
398398
/// NOTE: - As a C function, must not thrown C++ exceptions.
399399
/// - Error propagation via SetError to avoid any direct need
400400
/// of Python API. Due to this `SetError` may have to ensure the GIL is
@@ -419,17 +419,17 @@ pub type DLPackManagedTensorAllocator = Option<unsafe extern "C" fn(
419419
/// This function is exposed by the framework through the DLPackExchangeAPI.
420420
///
421421
/// # Arguments
422-
///
422+
///
423423
/// * `py_object` - The Python object to convert. Must have the same type
424-
/// as the one the `DLPackExchangeAPI` was discovered from.
424+
/// as the one the `DLPackExchangeAPI` was discovered from.
425425
/// * `out` - The output DLManagedTensorVersioned.
426-
///
426+
///
427427
/// # Returns
428-
///
428+
///
429429
/// The owning DLManagedTensorVersioned* or NULL on failure with a
430430
/// Python exception set. If the data cannot be described using DLPack
431431
/// this should be a BufferError if possible.
432-
///
432+
///
433433
/// NOTE: - As a C function, must not thrown C++ exceptions.
434434
///
435435
/// See also:
@@ -455,13 +455,13 @@ pub type DLPackManagedTensorFromPyObjectNoSync = Option<unsafe extern "C" fn(
455455
/// This function is exposed by the framework through the DLPackExchangeAPI.
456456
///
457457
/// # Arguments
458-
///
458+
///
459459
/// * `py_object` - The Python object to convert. Must have the same type
460-
/// as the one the `DLPackExchangeAPI` was discovered from.
460+
/// as the one the `DLPackExchangeAPI` was discovered from.
461461
/// * `out` - The output DLTensor, whose space is pre-allocated on stack.
462462
///
463463
/// # Returns
464-
///
464+
///
465465
/// 0 on success, -1 on failure with a Python exception set.
466466
///
467467
/// NOTE: - As a C function, must not thrown C++ exceptions.
@@ -485,15 +485,15 @@ pub type DLPackDLTensorFromPyObjectNoSync = Option<unsafe extern "C" fn(
485485
/// always set out_current_stream[0] to NULL.
486486
///
487487
/// # Arguments
488-
///
488+
///
489489
/// * `device_type` - The device type.
490490
/// * `device_id` - The device id.
491491
/// * `out_current_stream` - The output current work stream.
492492
///
493493
/// # Returns
494-
///
494+
///
495495
/// 0 on success, -1 on failure with a Python exception set.
496-
///
496+
///
497497
/// NOTE: - As a C function, must not thrown C++ exceptions.
498498
///
499499
/// See also:
@@ -514,15 +514,15 @@ pub type DLPackCurrentWorkStream = Option<unsafe extern "C" fn(
514514
/// This function is exposed by the framework through the DLPackExchangeAPI.
515515
///
516516
/// # Arguments
517-
///
517+
///
518518
/// * `tensor` - The DLManagedTensorVersioned to convert the ownership of the
519-
/// tensor is stolen.
519+
/// tensor is stolen.
520520
/// * `out_py_object` - The output Python object.
521-
///
521+
///
522522
/// # Returns
523-
///
523+
///
524524
/// 0 on success, -1 on failure with a Python exception set.
525-
///
525+
///
526526
/// See also:
527527
/// DLPackExchangeAPI
528528
pub type DLPackManagedTensorToPyObjectNoSync = Option<unsafe extern "C" fn(
@@ -552,9 +552,8 @@ pub struct DLPackExchangeAPIHeader {
552552
///
553553
/// Additionally to `__dlpack__()` we define a C function table sharable by
554554
///
555-
/// Python implementations via `__dlpack_c_exchange_api__`.
556-
/// This attribute must be set on the type as a Python PyCapsule
557-
/// with name "dlpack_exchange_api".
555+
/// Python implementations via `__dlpack_c_exchange_api__`. This attribute must
556+
/// be set on the type as a Python PyCapsule with name "dlpack_exchange_api".
558557
///
559558
/// A consumer library may use a pattern such as:
560559
///
@@ -600,28 +599,30 @@ pub struct DLPackExchangeAPIHeader {
600599
/// Guidelines for leveraging DLPackExchangeAPI:
601600
///
602601
/// There are generally two kinds of consumer needs for DLPack exchange:
603-
/// - N0: library support, where consumer.kernel(x, y, z) would like to run a kernel
604-
/// with the data from x, y, z. The consumer is also expected to run the kernel with the same
605-
/// stream context as the producer. For example, when x, y, z is torch.Tensor,
606-
/// consumer should query exchange_api->current_work_stream to get the
607-
/// current stream and launch the kernel with the same stream.
608-
/// This setup is necessary for no synchronization in kernel launch and maximum compatibility
609-
/// with CUDA graph capture in the producer.
610-
/// This is the desirable behavior for library extension support for frameworks like PyTorch.
602+
/// - N0: library support, where consumer.kernel(x, y, z) would like to run a
603+
/// kernel with the data from x, y, z. The consumer is also expected to run
604+
/// the kernel with the same stream context as the producer. For example, when
605+
/// x, y, z is torch.Tensor, consumer should query
606+
/// exchange_api->current_work_stream to get the current stream and launch the
607+
/// kernel with the same stream. This setup is necessary for no
608+
/// synchronization in kernel launch and maximum compatibility with CUDA graph
609+
/// capture in the producer. This is the desirable behavior for library
610+
/// extension support for frameworks like PyTorch.
611611
/// - N1: data ingestion and retention
612612
///
613-
/// Note that obj.__dlpack__() API should provide useful ways for N1.
614-
/// The primary focus of the current DLPackExchangeAPI is to enable faster exchange N0
615-
/// with the support of the function pointer current_work_stream.
613+
/// Note that obj.__dlpack__() API should provide useful ways for N1. The
614+
/// primary focus of the current DLPackExchangeAPI is to enable faster exchange
615+
/// N0 with the support of the function pointer current_work_stream.
616616
///
617-
/// Array/Tensor libraries should statically create and initialize this structure
618-
/// then return a pointer to DLPackExchangeAPI as an int value in Tensor/Array.
619-
/// The DLPackExchangeAPI* must stay alive throughout the lifetime of the process.
617+
/// Array/Tensor libraries should statically create and initialize this
618+
/// structure then return a pointer to DLPackExchangeAPI as an int value in
619+
/// Tensor/Array. The DLPackExchangeAPI* must stay alive throughout the lifetime
620+
/// of the process.
620621
///
621622
/// One simple way to do so is to create a static instance of DLPackExchangeAPI
622-
/// within the framework and return a pointer to it. The following code
623-
/// shows an example to do so in C++. It should also be reasonably easy
624-
/// to do so in other languages.
623+
/// within the framework and return a pointer to it. The following code shows an
624+
/// example to do so in C++. It should also be reasonably easy to do so in other
625+
/// languages.
625626
#[repr(C)]
626627
#[derive(Debug, Clone, Copy)]
627628
pub struct DLPackExchangeAPI {

0 commit comments

Comments
 (0)