aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndrew Waterman <andrew@sifive.com>2020-11-18 16:05:43 -0800
committerAndrew Waterman <andrew@sifive.com>2020-11-18 16:05:43 -0800
commit081bcaddc552b649bee9ebea14b6c73448f58a3a (patch)
treeb2f6c4471be650f6ae7592d4a9fccf1089c5691b
parentb2a2f24692192362c2d71d1d89cb22e01fde0a22 (diff)
downloadspike-081bcaddc552b649bee9ebea14b6c73448f58a3a.zip
spike-081bcaddc552b649bee9ebea14b6c73448f58a3a.tar.gz
spike-081bcaddc552b649bee9ebea14b6c73448f58a3a.tar.bz2
Avoid use of __builtin_popcount for portability
-rw-r--r--riscv/arith.h11
-rw-r--r--riscv/insns/bdep.h2
-rw-r--r--riscv/insns/bdepw.h2
-rw-r--r--riscv/insns/bext.h2
-rw-r--r--riscv/insns/bextw.h2
-rw-r--r--riscv/insns/bmatxor.h2
6 files changed, 16 insertions, 5 deletions
diff --git a/riscv/arith.h b/riscv/arith.h
index c9d3979..72bb515 100644
--- a/riscv/arith.h
+++ b/riscv/arith.h
@@ -121,6 +121,17 @@ static inline uint64_t make_mask64(int pos, int len)
return (UINT64_MAX >> (64 - len)) << pos;
}
+static inline int popcount(uint64_t val)
+{
+ val = (val & 0x5555555555555555U) + ((val >> 1) & 0x5555555555555555U);
+ val = (val & 0x3333333333333333U) + ((val >> 2) & 0x3333333333333333U);
+ val = (val & 0x0f0f0f0f0f0f0f0fU) + ((val >> 4) & 0x0f0f0f0f0f0f0f0fU);
+ val = (val & 0x00ff00ff00ff00ffU) + ((val >> 8) & 0x00ff00ff00ff00ffU);
+ val = (val & 0x0000ffff0000ffffU) + ((val >> 16) & 0x0000ffff0000ffffU);
+ val = (val & 0x00000000ffffffffU) + ((val >> 32) & 0x00000000ffffffffU);
+ return val;
+}
+
static inline int ctz(uint64_t val)
{
if (!val)
diff --git a/riscv/insns/bdep.h b/riscv/insns/bdep.h
index 92e2854..e71976f 100644
--- a/riscv/insns/bdep.h
+++ b/riscv/insns/bdep.h
@@ -3,7 +3,7 @@ uint64_t c = 0, i = 0, data = zext_xlen(RS1), mask = zext_xlen(RS2);
while (mask) {
uint64_t b = mask & ~((mask | (mask-1)) + 1);
c |= (data << (ctz(b) - i)) & b;
- i += __builtin_popcountl(b);
+ i += popcount(b);
mask -= b;
}
WRITE_RD(sext_xlen(c));
diff --git a/riscv/insns/bdepw.h b/riscv/insns/bdepw.h
index 882dbdd..1c06251 100644
--- a/riscv/insns/bdepw.h
+++ b/riscv/insns/bdepw.h
@@ -4,7 +4,7 @@ uint64_t c = 0, i = 0, data = zext32(RS1), mask = zext32(RS2);
while (mask) {
uint64_t b = mask & ~((mask | (mask-1)) + 1);
c |= (data << (ctz(b) - i)) & b;
- i += __builtin_popcountl(b);
+ i += popcount(b);
mask -= b;
}
WRITE_RD(sext32(c));
diff --git a/riscv/insns/bext.h b/riscv/insns/bext.h
index a03ea6f..b0ed4a8 100644
--- a/riscv/insns/bext.h
+++ b/riscv/insns/bext.h
@@ -3,7 +3,7 @@ uint64_t c = 0, i = 0, data = zext_xlen(RS1), mask = zext_xlen(RS2);
while (mask) {
uint64_t b = mask & ~((mask | (mask-1)) + 1);
c |= (data & b) >> (ctz(b) - i);
- i += __builtin_popcountl(b);
+ i += popcount(b);
mask -= b;
}
WRITE_RD(sext_xlen(c));
diff --git a/riscv/insns/bextw.h b/riscv/insns/bextw.h
index 5e6ee47..6837714 100644
--- a/riscv/insns/bextw.h
+++ b/riscv/insns/bextw.h
@@ -4,7 +4,7 @@ uint64_t c = 0, i = 0, data = zext32(RS1), mask = zext32(RS2);
while (mask) {
uint64_t b = mask & ~((mask | (mask-1)) + 1);
c |= (data & b) >> (ctz(b) - i);
- i += __builtin_popcountl(b);
+ i += popcount(b);
mask -= b;
}
WRITE_RD(sext32(c));
diff --git a/riscv/insns/bmatxor.h b/riscv/insns/bmatxor.h
index 06d9db0..e4dedfd 100644
--- a/riscv/insns/bmatxor.h
+++ b/riscv/insns/bmatxor.h
@@ -22,7 +22,7 @@ for (int i = 0; i < 8; i++) {
uint64_t x = 0;
for (int i = 0; i < 64; i++) {
- if (__builtin_popcountl(u[i / 8] & v[i % 8]) & 1)
+ if (popcount(u[i / 8] & v[i % 8]) & 1)
x |= 1LL << i;
}