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