Bug 1461556 - Don't memset-zero the BacktrackingAllocator::vregs array of non-trivial VirtualRegister instances. r=jandem
authorJeff Walden <jwalden@mit.edu>
Wed, 16 May 2018 10:45:08 -0700
changeset 418612 e016aa76775e
parent 418611 d8411d78d58a
child 418613 5d99c9233693
push id103351
push userjwalden@mit.edu
push dateThu, 17 May 2018 07:17:38 +0000
treeherdermozilla-inbound@e016aa76775e [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersjandem
bugs1461556
milestone62.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1461556 - Don't memset-zero the BacktrackingAllocator::vregs array of non-trivial VirtualRegister instances. r=jandem
js/src/jit/BacktrackingAllocator.cpp
js/src/jit/BacktrackingAllocator.h
--- a/js/src/jit/BacktrackingAllocator.cpp
+++ b/js/src/jit/BacktrackingAllocator.cpp
@@ -409,17 +409,16 @@ BacktrackingAllocator::init()
 
     liveIn = mir->allocate<BitSet>(graph.numBlockIds());
     if (!liveIn)
         return false;
 
     size_t numVregs = graph.numVirtualRegisters();
     if (!vregs.init(mir->alloc(), numVregs))
         return false;
-    memset(&vregs[0], 0, sizeof(VirtualRegister) * numVregs);
     for (uint32_t i = 0; i < numVregs; i++)
         new(&vregs[i]) VirtualRegister();
 
     // Build virtual register objects.
     for (size_t i = 0; i < graph.numBlocks(); i++) {
         if (mir->shouldCancel("Create data structures (main loop)"))
             return false;
 
@@ -1145,19 +1144,19 @@ BacktrackingAllocator::mergeAndQueueRegi
     // If there is an OSR block, merge parameters in that block with the
     // corresponding parameters in the initial block.
     if (MBasicBlock* osr = graph.mir().osrBlock()) {
         size_t original = 1;
         for (LInstructionIterator iter = osr->lir()->begin(); iter != osr->lir()->end(); iter++) {
             if (iter->isParameter()) {
                 for (size_t i = 0; i < iter->numDefs(); i++) {
                     DebugOnly<bool> found = false;
-                    VirtualRegister &paramVreg = vreg(iter->getDef(i));
+                    VirtualRegister& paramVreg = vreg(iter->getDef(i));
                     for (; original < paramVreg.vreg(); original++) {
-                        VirtualRegister &originalVreg = vregs[original];
+                        VirtualRegister& originalVreg = vregs[original];
                         if (*originalVreg.def()->output() == *iter->getDef(i)->output()) {
                             MOZ_ASSERT(originalVreg.ins()->isParameter());
                             if (!tryMergeBundles(originalVreg.firstBundle(), paramVreg.firstBundle()))
                                 return false;
                             found = true;
                             break;
                         }
                     }
@@ -1181,17 +1180,17 @@ BacktrackingAllocator::mergeAndQueueRegi
         }
     }
 
     // Try to merge phis with their inputs.
     for (size_t i = 0; i < graph.numBlocks(); i++) {
         LBlock* block = graph.getBlock(i);
         for (size_t j = 0; j < block->numPhis(); j++) {
             LPhi* phi = block->getPhi(j);
-            VirtualRegister &outputVreg = vreg(phi->getDef(0));
+            VirtualRegister& outputVreg = vreg(phi->getDef(0));
             for (size_t k = 0, kend = phi->numOperands(); k < kend; k++) {
                 VirtualRegister& inputVreg = vreg(phi->getOperand(k)->toUse());
                 if (!tryMergeBundles(inputVreg.firstBundle(), outputVreg.firstBundle()))
                     return false;
             }
         }
     }
 
@@ -1381,17 +1380,17 @@ BacktrackingAllocator::computeRequiremen
                                           Requirement *requirement, Requirement *hint)
 {
     // Set any requirement or hint on bundle according to its definition and
     // uses. Return false if there are conflicting requirements which will
     // require the bundle to be split.
 
     for (LiveRange::BundleLinkIterator iter = bundle->rangesBegin(); iter; iter++) {
         LiveRange* range = LiveRange::get(*iter);
-        VirtualRegister &reg = vregs[range->vreg()];
+        VirtualRegister& reg = vregs[range->vreg()];
 
         if (range->hasDefinition()) {
             // Deal with any definition constraints/hints.
             LDefinition::Policy policy = reg.def()->policy();
             if (policy == LDefinition::FIXED) {
                 // Fixed policies get a FIXED requirement.
                 JitSpew(JitSpew_RegAlloc, "  Requirement %s, fixed by definition",
                         reg.def()->output()->toString().get());
@@ -1443,17 +1442,17 @@ BacktrackingAllocator::tryAllocateRegist
 
     if (!r.allocatable)
         return true;
 
     LiveBundleVector aliasedConflicting;
 
     for (LiveRange::BundleLinkIterator iter = bundle->rangesBegin(); iter; iter++) {
         LiveRange* range = LiveRange::get(*iter);
-        VirtualRegister &reg = vregs[range->vreg()];
+        VirtualRegister& reg = vregs[range->vreg()];
 
         if (!reg.isCompatible(r.reg))
             return true;
 
         for (size_t a = 0; a < r.reg.numAliased(); a++) {
             PhysicalRegister& rAlias = registers[r.reg.aliased(a).code()];
             LiveRange* existing;
             if (!rAlias.allocations.contains(range, &existing))
--- a/js/src/jit/BacktrackingAllocator.h
+++ b/js/src/jit/BacktrackingAllocator.h
@@ -501,44 +501,41 @@ class LiveBundle : public TempObject
     UniqueChars toString() const;
 #endif
 };
 
 // Information about the allocation for a virtual register.
 class VirtualRegister
 {
     // Instruction which defines this register.
-    LNode* ins_;
+    LNode* ins_ = nullptr;
 
     // Definition in the instruction for this register.
-    LDefinition* def_;
+    LDefinition* def_ = nullptr;
 
     // All live ranges for this register. These may overlap each other, and are
     // ordered by their start position.
     InlineForwardList<LiveRange::RegisterLink> ranges_;
 
     // Whether def_ is a temp or an output.
-    bool isTemp_;
+    bool isTemp_ = false;
 
     // Whether this vreg is an input for some phi. This use is not reflected in
     // any range on the vreg.
-    bool usedByPhi_;
+    bool usedByPhi_ = false;
 
     // If this register's definition is MUST_REUSE_INPUT, whether a copy must
     // be introduced before the definition that relaxes the policy.
-    bool mustCopyInput_;
+    bool mustCopyInput_ = false;
 
     void operator=(const VirtualRegister&) = delete;
     VirtualRegister(const VirtualRegister&) = delete;
 
   public:
-    explicit VirtualRegister()
-    {
-        // Note: This class is zeroed before it is constructed.
-    }
+    VirtualRegister() = default;
 
     void init(LNode* ins, LDefinition* def, bool isTemp) {
         MOZ_ASSERT(!ins_);
         ins_ = ins;
         def_ = def;
         isTemp_ = isTemp;
     }