use crate::active_set::ActiveSet;
use core::marker::PhantomData;
#[must_use = "dropping a Warp without merging may indicate a missing merge — \
both branches of a diverge should be merged before shuffling"]
pub struct Warp<S: ActiveSet> {
_phantom: PhantomData<S>,
}
impl Warp<crate::active_set::All> {
pub fn kernel_entry() -> Self {
Warp {
_phantom: PhantomData,
}
}
}
impl<S: ActiveSet> Warp<S> {
pub(crate) fn new() -> Self {
Warp {
_phantom: PhantomData,
}
}
pub fn active_set_name(&self) -> &'static str {
S::NAME
}
pub fn active_mask(&self) -> u64 {
S::MASK
}
pub fn population(&self) -> u32 {
S::MASK.count_ones()
}
pub fn sync(&self) {
}
}
impl<S: ActiveSet> core::fmt::Debug for Warp<S> {
fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
write!(f, "Warp<{}>(mask={:016X})", S::NAME, S::MASK)
}
}
#[cfg(test)]
mod tests {
use super::*;
use crate::active_set::*;
#[test]
fn test_warp_all() {
let w: Warp<All> = Warp::new();
assert_eq!(w.active_set_name(), "All");
assert_eq!(w.active_mask(), All::MASK);
assert_eq!(w.population(), crate::WARP_SIZE);
}
#[test]
fn test_warp_even() {
let w: Warp<Even> = Warp::new();
assert_eq!(w.active_set_name(), "Even");
assert_eq!(w.population(), crate::WARP_SIZE / 2);
}
#[test]
fn test_warp_kernel_entry() {
let w: Warp<All> = Warp::kernel_entry();
assert_eq!(w.population(), crate::WARP_SIZE);
}
#[test]
fn test_warp_debug() {
let w: Warp<Even> = Warp::new();
let s = format!("{:?}", w);
assert!(s.contains("Even"));
}
#[test]
fn test_sync_any_active_set() {
let all: Warp<All> = Warp::new();
let even: Warp<Even> = Warp::new();
let odd: Warp<Odd> = Warp::new();
all.sync();
even.sync();
odd.sync();
}
}