diff --git a/rocket/src/main/scala/util.scala b/rocket/src/main/scala/util.scala index da2343e3..34277543 100644 --- a/rocket/src/main/scala/util.scala +++ b/rocket/src/main/scala/util.scala @@ -32,6 +32,41 @@ object FillInterleaved } } +// http://aggregate.ee.engr.uky.edu/MAGIC/#Population%20Count%20%28Ones%20Count%29 +// http://bits.stephan-brumme.com/countBits.html +object PopCount +{ + def apply(in: Bits) = + { + require(in.width <= 32) + val w = log2up(in.width+1) + var x = in + if(in.width == 2) { + x = x - ((x >> UFix(1)) & Bits("h_5555_5555")) + } else if(in.width <= 4) { + x = x - ((x >> UFix(1)) & Bits("h_5555_5555")) + x = (((x >> UFix(2)) & Bits("h_3333_3333")) + (x & Bits("h_3333_3333"))) + } else if(in.width <= 8) { + x = x - ((x >> UFix(1)) & Bits("h_5555_5555")) + x = (((x >> UFix(2)) & Bits("h_3333_3333")) + (x & Bits("h_3333_3333"))) + x = ((x >> UFix(4)) + x) + } else { + // count bits of each 2-bit chunk + x = x - ((x >> UFix(1)) & Bits("h_5555_5555")) + // count bits of each 4-bit chunk + x = (((x >> UFix(2)) & Bits("h_3333_3333")) + (x & Bits("h_3333_3333"))) + // count bits of each 8-bit chunk + x = ((x >> UFix(4)) + x) + // mask junk in upper bits + x = x & Bits("h_0f0f_0f0f") + // add all four 8-bit chunks + x = x + (x >> UFix(8)) + x = x + (x >> UFix(16)) + } + x(w-1,0) + } +} + object Reverse { def apply(in: Bits) =