Skip to main content

velesdb_core/
gpu.rs

1//! GPU-accelerated vector operations using wgpu (WebGPU).
2//!
3//! This module provides optional GPU acceleration for batch distance calculations.
4//! Enable with feature flag `gpu`.
5//!
6//! # When to use GPU
7//!
8//! - **Batch operations** (100+ queries at once)
9//! - **Large datasets** (500K+ vectors)
10//! - **Index construction** (HNSW graph building)
11//!
12//! For single queries on datasets ≤100K, CPU SIMD remains faster.
13//!
14//! # Platform Support
15//!
16//! | Platform | Backend |
17//! |----------|---------|
18//! | Windows | DirectX 12 / Vulkan |
19//! | macOS | Metal |
20//! | Linux | Vulkan |
21//! | Browser | WebGPU |
22
23#[cfg(feature = "gpu")]
24#[path = "gpu/helpers.rs"]
25mod helpers;
26
27#[cfg(feature = "gpu")]
28#[path = "gpu/gpu_backend.rs"]
29mod gpu_backend;
30
31#[cfg(all(test, feature = "gpu"))]
32#[path = "gpu/gpu_backend_tests.rs"]
33mod gpu_backend_tests;
34
35#[cfg(all(test, feature = "gpu", feature = "persistence"))]
36#[path = "gpu/gpu_csr_tests.rs"]
37mod gpu_csr_extended_tests;
38
39#[cfg(feature = "gpu")]
40#[path = "gpu/pq_gpu.rs"]
41pub mod pq_gpu;
42
43#[cfg(all(feature = "gpu", feature = "persistence"))]
44#[path = "gpu/gpu_csr.rs"]
45pub mod gpu_csr;
46
47#[cfg(all(feature = "gpu", feature = "persistence"))]
48#[path = "gpu/gpu_traversal_buffers.rs"]
49mod gpu_traversal_buffers;
50
51#[cfg(all(feature = "gpu", feature = "persistence"))]
52#[path = "gpu/gpu_traversal_pipelines.rs"]
53mod gpu_traversal_pipelines;
54
55#[cfg(all(feature = "gpu", feature = "persistence"))]
56#[path = "gpu/gpu_traversal.rs"]
57pub mod gpu_traversal;
58
59#[cfg(feature = "gpu")]
60pub use gpu_backend::GpuAccelerator;
61#[cfg(all(feature = "gpu", feature = "persistence"))]
62pub use gpu_traversal::{should_traverse_gpu, GpuTraversalContext, GpuTraversalStats};
63#[cfg(feature = "gpu")]
64pub use pq_gpu::{gpu_kmeans_assign, should_use_gpu, PqGpuContext};
65
66/// Check if GPU dispatch is worthwhile (always false without gpu feature).
67#[cfg(not(feature = "gpu"))]
68#[must_use]
69pub fn should_use_gpu(_n: usize, _k: usize, _subspace_dim: usize) -> bool {
70    false
71}
72
73/// Check if GPU traversal is worthwhile (always false without GPU HNSW traversal support).
74#[cfg(not(all(feature = "gpu", feature = "persistence")))]
75#[must_use]
76pub fn should_traverse_gpu(_num_vectors: usize, _dimension: usize) -> bool {
77    false
78}
79
80/// Compute backend selection.
81#[derive(Debug, Clone, Copy, PartialEq, Eq, Default)]
82#[allow(dead_code)] // Used only when `gpu` feature is active
83pub(crate) enum ComputeBackend {
84    /// CPU SIMD (default, always available)
85    #[default]
86    Simd,
87    /// GPU via wgpu (requires `gpu` feature)
88    #[cfg(feature = "gpu")]
89    Gpu,
90}
91
92#[allow(dead_code)] // Used only when `gpu` feature is active
93impl ComputeBackend {
94    /// Returns the best available backend.
95    ///
96    /// Prefers GPU if available, falls back to SIMD.
97    #[must_use]
98    pub fn best_available() -> Self {
99        #[cfg(feature = "gpu")]
100        {
101            if gpu_backend::GpuAccelerator::is_available() {
102                return Self::Gpu;
103            }
104        }
105        Self::Simd
106    }
107
108    /// Returns true if GPU backend is available.
109    #[must_use]
110    pub fn gpu_available() -> bool {
111        #[cfg(feature = "gpu")]
112        {
113            gpu_backend::GpuAccelerator::is_available()
114        }
115        #[cfg(not(feature = "gpu"))]
116        {
117            false
118        }
119    }
120}