Skip to content

Commit 11fb083

Browse files
committed
feat(fingerprint): multi-lane SIMD views + bundle majority vote
QW4: chunks_u64x8() — iterate as 8-word batches for VPOPCNTDQ chunks_u8x64() — iterate as 64-byte batches for U8x64 ops bundle() — majority vote across multiple fingerprints These enable the Layer 1 cascade: sweep a fingerprint column via SIMD-width chunks, then bundle consensus across agents. https://claude.ai/code/session_01SbYsmmbPf9YQuYbHZN52Zh
1 parent 06dbae0 commit 11fb083

1 file changed

Lines changed: 41 additions & 0 deletions

File tree

src/hpc/fingerprint.rs

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -182,6 +182,47 @@ impl<const N: usize> Fingerprint<N> {
182182
&self.words
183183
}
184184

185+
/// Multi-lane SIMD view: iterate fingerprint as batches of 8 u64 words.
186+
///
187+
/// At N=256 (16K fingerprint), this yields 32 chunks of 8 words each.
188+
/// Each chunk is one AVX-512 VPOPCNTDQ iteration (512 bits at a time).
189+
/// Consumer uses `U64x8::from_slice(chunk)` for SIMD popcount.
190+
#[inline]
191+
pub fn chunks_u64x8(&self) -> impl Iterator<Item = &[u64]> {
192+
self.words.chunks(8)
193+
}
194+
195+
/// Multi-lane SIMD view: iterate as batches of 64 bytes.
196+
///
197+
/// At N=256 (16K fingerprint), yields 32 chunks of 64 bytes.
198+
/// Each chunk = one U8x64 load for byte-level SIMD ops.
199+
#[inline]
200+
pub fn chunks_u8x64(&self) -> impl Iterator<Item = &[u8]> {
201+
self.as_bytes().chunks(64)
202+
}
203+
204+
/// Bundle (majority vote) across multiple fingerprints.
205+
///
206+
/// Returns a new fingerprint where each bit is set if more than
207+
/// half of the input fingerprints have it set.
208+
pub fn bundle(items: &[&Self]) -> Self {
209+
let n = items.len();
210+
if n == 0 { return Self::zero(); }
211+
let threshold = n / 2;
212+
let mut result = [0u64; N];
213+
for w in 0..N {
214+
for bit in 0..64 {
215+
let count: usize = items.iter()
216+
.filter(|fp| (fp.words[w] >> bit) & 1 == 1)
217+
.count();
218+
if count > threshold {
219+
result[w] |= 1u64 << bit;
220+
}
221+
}
222+
}
223+
Self { words: result }
224+
}
225+
185226
/// Create from content string (SHA-256-like hash expansion).
186227
pub fn from_content(data: &str) -> Self {
187228
let mut h = 0x736f6d6570736575u64;

0 commit comments

Comments
 (0)