nv50/ir/util: fix BitSet issues
authorChristoph Bumiller <e0425955@student.tuwien.ac.at>
Fri, 5 Sep 2014 21:52:45 +0000 (23:52 +0200)
committerIlia Mirkin <imirkin@alum.mit.edu>
Sat, 6 Sep 2014 03:05:42 +0000 (23:05 -0400)
BitSet::allocate() is being used with the expectation that it would
leave the bitfield untouched if its size hasn't changed, however,
the function always zeroed the last word, which led to obscure bugs
with live set computation.

This also fixes BitSet::resize(), which was broken, but luckily not
being used.

Cc: "10.2 10.3" <mesa-stable@lists.freedesktop.org>
Reviewed-by: Ilia Mirkin <imirkin@alum.mit.edu>
src/gallium/drivers/nouveau/codegen/nv50_ir_ra.cpp
src/gallium/drivers/nouveau/codegen/nv50_ir_util.cpp
src/gallium/drivers/nouveau/codegen/nv50_ir_util.h

index 5ab6570175db99e79c83b9d2dd8448017ffd3b45..4b105b453c3fd99b1fb20c4945b33cb90be22778 100644 (file)
@@ -1657,6 +1657,10 @@ RegAlloc::execFunc()
            ret && i <= func->loopNestingBound;
            sequence = func->cfg.nextSequence(), ++i)
          ret = buildLiveSets(BasicBlock::get(func->cfg.getRoot()));
+      // reset marker
+      for (ArrayList::Iterator bi = func->allBBlocks.iterator();
+           !bi.end(); bi.next())
+         BasicBlock::get(bi)->liveSet.marker = false;
       if (!ret)
          break;
       func->orderInstructions(this->insns);
index 895977710cacafd93c68549b97df4d5a8da86a1c..d26acb304bc82cec586aca1b5f15b18026211f2e 100644 (file)
@@ -254,7 +254,9 @@ bool BitSet::resize(unsigned int nBits)
       return false;
    }
    if (n > p)
-      memset(&data[4 * p + 4], 0, (n - p) * 4);
+      memset(&data[p], 0, (n - p) * 4);
+   if (nBits < size && (nBits % 32))
+      data[(nBits + 31) / 32 - 1] &= (1 << (nBits % 32)) - 1;
 
    size = nBits;
    return true;
@@ -274,8 +276,8 @@ bool BitSet::allocate(unsigned int nBits, bool zero)
    if (zero)
       memset(data, 0, (size + 7) / 8);
    else
-   if (nBits)
-      data[(size + 31) / 32 - 1] = 0; // clear unused bits (e.g. for popCount)
+   if (size % 32) // clear unused bits (e.g. for popCount)
+      data[(size + 31) / 32 - 1] &= (1 << (size % 32)) - 1;
 
    return data;
 }
index a4ea9d981e0b1f878085d9e402539a3a31ccea64..fa2c4804a422a8f0696a9665e21ce983b551dae5 100644 (file)
@@ -484,6 +484,7 @@ public:
          FREE(data);
    }
 
+   // allocate will keep old data iff size is unchanged
    bool allocate(unsigned int nBits, bool zero);
    bool resize(unsigned int nBits); // keep old data, zero additional bits