scirs2-linalg 0.4.0

Linear algebra module for SciRS2 (scirs2-linalg)
Documentation
//! Metal backend implementation for Apple GPU acceleration
//!
//! This module provides a Metal backend for GPU acceleration on macOS and iOS devices.
//! Metal is Apple's low-level GPU programming framework for Apple silicon devices.

use super::common::*;

/// Placeholder Metal backend (requires Metal feature - macOS/iOS only)
#[cfg(feature = "metal")]
pub mod metal_impl {
    use super::*;

    pub struct MetalBackend {
        #[allow(dead_code)]
        device_registry: HashMap<String, String>,
    }

    impl MetalBackend {
        pub fn new() -> LinalgResult<Self> {
            // In a real implementation, this would initialize Metal
            Ok(Self {
                device_registry: HashMap::new(),
            })
        }
    }

    impl GpuBackend for MetalBackend {
        fn name(&self) -> &str {
            "Metal"
        }

        fn is_available(&self) -> bool {
            // In a real implementation, check Metal availability (macOS/iOS only)
            cfg!(target_os = "macos") || cfg!(target_os = "ios")
        }

        fn list_devices(&self) -> LinalgResult<Vec<GpuDeviceInfo>> {
            // In a real implementation, enumerate Metal devices
            Ok(vec![])
        }

        fn create_context(&self, _device_id: usize) -> LinalgResult<Box<dyn GpuContext>> {
            Err(LinalgError::ComputationError(
                "Metal backend not fully implemented".to_string(),
            ))
        }
    }
}

// Re-export the Metal backend when the feature is enabled
#[cfg(feature = "metal")]
pub use metal_impl::*;

// Provide a stub when Metal is not available
#[cfg(not(feature = "metal"))]
pub struct MetalBackend;

#[cfg(not(feature = "metal"))]
impl MetalBackend {
    pub fn new() -> LinalgResult<Self> {
        Err(LinalgError::ComputationError(
            "Metal support not compiled in".to_string(),
        ))
    }
}

#[cfg(not(feature = "metal"))]
impl GpuBackend for MetalBackend {
    fn name(&self) -> &str {
        "Metal (not available)"
    }

    fn is_available(&self) -> bool {
        false
    }

    fn list_devices(&self) -> LinalgResult<Vec<GpuDeviceInfo>> {
        Ok(vec![])
    }

    fn create_context(&self, _device_id: usize) -> LinalgResult<Box<dyn GpuContext>> {
        Err(LinalgError::ComputationError(
            "Metal support not compiled in".to_string(),
        ))
    }
}