Skip to content
This repository

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse code

pure rust implementation of the CTPOP population count instruction

  • Loading branch information...
commit c5286f2f60eb4d919e422fbc4759a6909f2e76dd 1 parent 63a138a
Steve Jenson authored December 09, 2012
2  README.md
Source Rendered
@@ -7,3 +7,5 @@
7 7
 `tree.rs` - A purely functional binary search tree. Currently lacks delete.
8 8
 
9 9
 `red_black_tree.rs` - A purely functional red-black tree.
  10
+
  11
+`ctpop.rs` - A Rust implementation of the population count (native CTPOP instruction)
1  crate.rc
@@ -21,5 +21,6 @@ pub mod tree;
21 21
 pub mod lazy;
22 22
 pub mod pairing_heap;
23 23
 pub mod red_black_tree;
  24
+pub mod ctpop;
24 25
 
25 26
 mod test_tree;
40  ctpop.rs
... ...
@@ -0,0 +1,40 @@
  1
+/**
  2
+ * Count the Population of an unsigned integer. Returns how many bits are
  3
+ * set to 1.
  4
+ *
  5
+ * Currently designed for a 32-bit unsigned integer.
  6
+ *
  7
+ * Many chips have a CTPOP instruction available and would be an order
  8
+ * of magnitude speed improvement.
  9
+ */
  10
+pure fn ctpop32(map : u32) -> u32 {
  11
+  // Code smell: these constants should not be defined in the function.
  12
+  let SK5  : u32 = 0x55555555;
  13
+  let SK3  : u32 = 0x33333333;
  14
+  let SKF0 : u32 = 0xF0F0F0F;
  15
+  let SKFF : u32 = 0xFF00FF;
  16
+  let mut Map = copy map;
  17
+
  18
+  Map-=((Map>>1)&SK5);
  19
+  Map=(Map&SK3)+((Map>>2)&SK3);
  20
+  Map=(Map&SKF0)+((Map>>4)&SKF0);
  21
+  Map+=Map>>8;
  22
+
  23
+  return (Map+(Map>>16))&0x3F;
  24
+}
  25
+
  26
+#[test]
  27
+fn test_ctpop32() {
  28
+  assert(ctpop32(0x0) == 0);
  29
+  assert(ctpop32(0x1) == 1);
  30
+  assert(ctpop32(0x3) == 2);
  31
+  assert(ctpop32(0x7) == 3);
  32
+  assert(ctpop32(0xF) == 4);
  33
+  assert(ctpop32(0x10) == 1);
  34
+  assert(ctpop32(0xFF) == 8);
  35
+  assert(ctpop32(0xAD) == 5);
  36
+  assert(ctpop32(0x2FADBFF) == 21);
  37
+  assert(ctpop32(0x82FFFFFF) == 26);
  38
+  assert(ctpop32(0x8FFFFFFF) == 29);
  39
+  assert(ctpop32(0xFFFFFFFF) == 32);
  40
+}

0 notes on commit c5286f2

Please sign in to comment.
Something went wrong with that request. Please try again.